1 /* Tree lowering pass.  This pass converts the GENERIC functions-as-trees
2    tree representation into the GIMPLE form.
3    Copyright (C) 2002-2021 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>.
6 
7 This file is part of GCC.
8 
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.
13 
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.
18 
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/>.  */
22 
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 "memmodel.h"
31 #include "tm_p.h"
32 #include "gimple.h"
33 #include "gimple-predict.h"
34 #include "tree-pass.h"		/* FIXME: only for PROP_gimple_any */
35 #include "ssa.h"
36 #include "cgraph.h"
37 #include "tree-pretty-print.h"
38 #include "diagnostic-core.h"
39 #include "alias.h"
40 #include "fold-const.h"
41 #include "calls.h"
42 #include "varasm.h"
43 #include "stmt.h"
44 #include "expr.h"
45 #include "gimple-fold.h"
46 #include "tree-eh.h"
47 #include "gimplify.h"
48 #include "gimple-iterator.h"
49 #include "stor-layout.h"
50 #include "print-tree.h"
51 #include "tree-iterator.h"
52 #include "tree-inline.h"
53 #include "langhooks.h"
54 #include "tree-cfg.h"
55 #include "tree-ssa.h"
56 #include "omp-general.h"
57 #include "omp-low.h"
58 #include "gimple-low.h"
59 #include "gomp-constants.h"
60 #include "splay-tree.h"
61 #include "gimple-walk.h"
62 #include "langhooks-def.h"	/* FIXME: for lhd_set_decl_assembler_name */
63 #include "builtins.h"
64 #include "stringpool.h"
65 #include "attribs.h"
66 #include "asan.h"
67 #include "dbgcnt.h"
68 #include "omp-offload.h"
69 #include "context.h"
70 #include "tree-nested.h"
71 
72 /* Hash set of poisoned variables in a bind expr.  */
73 static hash_set<tree> *asan_poisoned_variables = NULL;
74 
75 enum gimplify_omp_var_data
76 {
77   GOVD_SEEN = 0x000001,
78   GOVD_EXPLICIT = 0x000002,
79   GOVD_SHARED = 0x000004,
80   GOVD_PRIVATE = 0x000008,
81   GOVD_FIRSTPRIVATE = 0x000010,
82   GOVD_LASTPRIVATE = 0x000020,
83   GOVD_REDUCTION = 0x000040,
84   GOVD_LOCAL = 0x00080,
85   GOVD_MAP = 0x000100,
86   GOVD_DEBUG_PRIVATE = 0x000200,
87   GOVD_PRIVATE_OUTER_REF = 0x000400,
88   GOVD_LINEAR = 0x000800,
89   GOVD_ALIGNED = 0x001000,
90 
91   /* Flag for GOVD_MAP: don't copy back.  */
92   GOVD_MAP_TO_ONLY = 0x002000,
93 
94   /* Flag for GOVD_LINEAR or GOVD_LASTPRIVATE: no outer reference.  */
95   GOVD_LINEAR_LASTPRIVATE_NO_OUTER = 0x004000,
96 
97   GOVD_MAP_0LEN_ARRAY = 0x008000,
98 
99   /* Flag for GOVD_MAP, if it is always, to or always, tofrom mapping.  */
100   GOVD_MAP_ALWAYS_TO = 0x010000,
101 
102   /* Flag for shared vars that are or might be stored to in the region.  */
103   GOVD_WRITTEN = 0x020000,
104 
105   /* Flag for GOVD_MAP, if it is a forced mapping.  */
106   GOVD_MAP_FORCE = 0x040000,
107 
108   /* Flag for GOVD_MAP: must be present already.  */
109   GOVD_MAP_FORCE_PRESENT = 0x080000,
110 
111   /* Flag for GOVD_MAP: only allocate.  */
112   GOVD_MAP_ALLOC_ONLY = 0x100000,
113 
114   /* Flag for GOVD_MAP: only copy back.  */
115   GOVD_MAP_FROM_ONLY = 0x200000,
116 
117   GOVD_NONTEMPORAL = 0x400000,
118 
119   /* Flag for GOVD_LASTPRIVATE: conditional modifier.  */
120   GOVD_LASTPRIVATE_CONDITIONAL = 0x800000,
121 
122   GOVD_CONDTEMP = 0x1000000,
123 
124   /* Flag for GOVD_REDUCTION: inscan seen in {in,ex}clusive clause.  */
125   GOVD_REDUCTION_INSCAN = 0x2000000,
126 
127   /* Flag for GOVD_MAP: (struct) vars that have pointer attachments for
128      fields.  */
129   GOVD_MAP_HAS_ATTACHMENTS = 8388608,
130 
131   GOVD_DATA_SHARE_CLASS = (GOVD_SHARED | GOVD_PRIVATE | GOVD_FIRSTPRIVATE
132 			   | GOVD_LASTPRIVATE | GOVD_REDUCTION | GOVD_LINEAR
133 			   | GOVD_LOCAL)
134 };
135 
136 
137 enum omp_region_type
138 {
139   ORT_WORKSHARE = 0x00,
140   ORT_TASKGROUP = 0x01,
141   ORT_SIMD 	= 0x04,
142 
143   ORT_PARALLEL	= 0x08,
144   ORT_COMBINED_PARALLEL = ORT_PARALLEL | 1,
145 
146   ORT_TASK	= 0x10,
147   ORT_UNTIED_TASK = ORT_TASK | 1,
148   ORT_TASKLOOP  = ORT_TASK | 2,
149   ORT_UNTIED_TASKLOOP = ORT_UNTIED_TASK | 2,
150 
151   ORT_TEAMS	= 0x20,
152   ORT_COMBINED_TEAMS = ORT_TEAMS | 1,
153   ORT_HOST_TEAMS = ORT_TEAMS | 2,
154   ORT_COMBINED_HOST_TEAMS = ORT_COMBINED_TEAMS | 2,
155 
156   /* Data region.  */
157   ORT_TARGET_DATA = 0x40,
158 
159   /* Data region with offloading.  */
160   ORT_TARGET	= 0x80,
161   ORT_COMBINED_TARGET = ORT_TARGET | 1,
162   ORT_IMPLICIT_TARGET = ORT_TARGET | 2,
163 
164   /* OpenACC variants.  */
165   ORT_ACC	= 0x100,  /* A generic OpenACC region.  */
166   ORT_ACC_DATA	= ORT_ACC | ORT_TARGET_DATA, /* Data construct.  */
167   ORT_ACC_PARALLEL = ORT_ACC | ORT_TARGET,  /* Parallel construct */
168   ORT_ACC_KERNELS  = ORT_ACC | ORT_TARGET | 2,  /* Kernels construct.  */
169   ORT_ACC_SERIAL   = ORT_ACC | ORT_TARGET | 4,  /* Serial construct.  */
170   ORT_ACC_HOST_DATA = ORT_ACC | ORT_TARGET_DATA | 2,  /* Host data.  */
171 
172   /* Dummy OpenMP region, used to disable expansion of
173      DECL_VALUE_EXPRs in taskloop pre body.  */
174   ORT_NONE	= 0x200
175 };
176 
177 /* Gimplify hashtable helper.  */
178 
179 struct gimplify_hasher : free_ptr_hash <elt_t>
180 {
181   static inline hashval_t hash (const elt_t *);
182   static inline bool equal (const elt_t *, const elt_t *);
183 };
184 
185 struct gimplify_ctx
186 {
187   struct gimplify_ctx *prev_context;
188 
189   vec<gbind *> bind_expr_stack;
190   tree temps;
191   gimple_seq conditional_cleanups;
192   tree exit_label;
193   tree return_temp;
194 
195   vec<tree> case_labels;
196   hash_set<tree> *live_switch_vars;
197   /* The formal temporary table.  Should this be persistent?  */
198   hash_table<gimplify_hasher> *temp_htab;
199 
200   int conditions;
201   unsigned into_ssa : 1;
202   unsigned allow_rhs_cond_expr : 1;
203   unsigned in_cleanup_point_expr : 1;
204   unsigned keep_stack : 1;
205   unsigned save_stack : 1;
206   unsigned in_switch_expr : 1;
207 };
208 
209 enum gimplify_defaultmap_kind
210 {
211   GDMK_SCALAR,
212   GDMK_AGGREGATE,
213   GDMK_ALLOCATABLE,
214   GDMK_POINTER
215 };
216 
217 struct gimplify_omp_ctx
218 {
219   struct gimplify_omp_ctx *outer_context;
220   splay_tree variables;
221   hash_set<tree> *privatized_types;
222   tree clauses;
223   /* Iteration variables in an OMP_FOR.  */
224   vec<tree> loop_iter_var;
225   location_t location;
226   enum omp_clause_default_kind default_kind;
227   enum omp_region_type region_type;
228   enum tree_code code;
229   bool combined_loop;
230   bool distribute;
231   bool target_firstprivatize_array_bases;
232   bool add_safelen1;
233   bool order_concurrent;
234   bool has_depend;
235   bool in_for_exprs;
236   int defaultmap[4];
237 };
238 
239 static struct gimplify_ctx *gimplify_ctxp;
240 static struct gimplify_omp_ctx *gimplify_omp_ctxp;
241 static bool in_omp_construct;
242 
243 /* Forward declaration.  */
244 static enum gimplify_status gimplify_compound_expr (tree *, gimple_seq *, bool);
245 static hash_map<tree, tree> *oacc_declare_returns;
246 static enum gimplify_status gimplify_expr (tree *, gimple_seq *, gimple_seq *,
247 					   bool (*) (tree), fallback_t, bool);
248 
249 /* Shorter alias name for the above function for use in gimplify.c
250    only.  */
251 
252 static inline void
gimplify_seq_add_stmt(gimple_seq * seq_p,gimple * gs)253 gimplify_seq_add_stmt (gimple_seq *seq_p, gimple *gs)
254 {
255   gimple_seq_add_stmt_without_update (seq_p, gs);
256 }
257 
258 /* Append sequence SRC to the end of sequence *DST_P.  If *DST_P is
259    NULL, a new sequence is allocated.   This function is
260    similar to gimple_seq_add_seq, but does not scan the operands.
261    During gimplification, we need to manipulate statement sequences
262    before the def/use vectors have been constructed.  */
263 
264 static void
gimplify_seq_add_seq(gimple_seq * dst_p,gimple_seq src)265 gimplify_seq_add_seq (gimple_seq *dst_p, gimple_seq src)
266 {
267   gimple_stmt_iterator si;
268 
269   if (src == NULL)
270     return;
271 
272   si = gsi_last (*dst_p);
273   gsi_insert_seq_after_without_update (&si, src, GSI_NEW_STMT);
274 }
275 
276 
277 /* Pointer to a list of allocated gimplify_ctx structs to be used for pushing
278    and popping gimplify contexts.  */
279 
280 static struct gimplify_ctx *ctx_pool = NULL;
281 
282 /* Return a gimplify context struct from the pool.  */
283 
284 static inline struct gimplify_ctx *
ctx_alloc(void)285 ctx_alloc (void)
286 {
287   struct gimplify_ctx * c = ctx_pool;
288 
289   if (c)
290     ctx_pool = c->prev_context;
291   else
292     c = XNEW (struct gimplify_ctx);
293 
294   memset (c, '\0', sizeof (*c));
295   return c;
296 }
297 
298 /* Put gimplify context C back into the pool.  */
299 
300 static inline void
ctx_free(struct gimplify_ctx * c)301 ctx_free (struct gimplify_ctx *c)
302 {
303   c->prev_context = ctx_pool;
304   ctx_pool = c;
305 }
306 
307 /* Free allocated ctx stack memory.  */
308 
309 void
free_gimplify_stack(void)310 free_gimplify_stack (void)
311 {
312   struct gimplify_ctx *c;
313 
314   while ((c = ctx_pool))
315     {
316       ctx_pool = c->prev_context;
317       free (c);
318     }
319 }
320 
321 
322 /* Set up a context for the gimplifier.  */
323 
324 void
push_gimplify_context(bool in_ssa,bool rhs_cond_ok)325 push_gimplify_context (bool in_ssa, bool rhs_cond_ok)
326 {
327   struct gimplify_ctx *c = ctx_alloc ();
328 
329   c->prev_context = gimplify_ctxp;
330   gimplify_ctxp = c;
331   gimplify_ctxp->into_ssa = in_ssa;
332   gimplify_ctxp->allow_rhs_cond_expr = rhs_cond_ok;
333 }
334 
335 /* Tear down a context for the gimplifier.  If BODY is non-null, then
336    put the temporaries into the outer BIND_EXPR.  Otherwise, put them
337    in the local_decls.
338 
339    BODY is not a sequence, but the first tuple in a sequence.  */
340 
341 void
pop_gimplify_context(gimple * body)342 pop_gimplify_context (gimple *body)
343 {
344   struct gimplify_ctx *c = gimplify_ctxp;
345 
346   gcc_assert (c
347               && (!c->bind_expr_stack.exists ()
348 		  || c->bind_expr_stack.is_empty ()));
349   c->bind_expr_stack.release ();
350   gimplify_ctxp = c->prev_context;
351 
352   if (body)
353     declare_vars (c->temps, body, false);
354   else
355     record_vars (c->temps);
356 
357   delete c->temp_htab;
358   c->temp_htab = NULL;
359   ctx_free (c);
360 }
361 
362 /* Push a GIMPLE_BIND tuple onto the stack of bindings.  */
363 
364 static void
gimple_push_bind_expr(gbind * bind_stmt)365 gimple_push_bind_expr (gbind *bind_stmt)
366 {
367   gimplify_ctxp->bind_expr_stack.reserve (8);
368   gimplify_ctxp->bind_expr_stack.safe_push (bind_stmt);
369 }
370 
371 /* Pop the first element off the stack of bindings.  */
372 
373 static void
gimple_pop_bind_expr(void)374 gimple_pop_bind_expr (void)
375 {
376   gimplify_ctxp->bind_expr_stack.pop ();
377 }
378 
379 /* Return the first element of the stack of bindings.  */
380 
381 gbind *
gimple_current_bind_expr(void)382 gimple_current_bind_expr (void)
383 {
384   return gimplify_ctxp->bind_expr_stack.last ();
385 }
386 
387 /* Return the stack of bindings created during gimplification.  */
388 
389 vec<gbind *>
gimple_bind_expr_stack(void)390 gimple_bind_expr_stack (void)
391 {
392   return gimplify_ctxp->bind_expr_stack;
393 }
394 
395 /* Return true iff there is a COND_EXPR between us and the innermost
396    CLEANUP_POINT_EXPR.  This info is used by gimple_push_cleanup.  */
397 
398 static bool
gimple_conditional_context(void)399 gimple_conditional_context (void)
400 {
401   return gimplify_ctxp->conditions > 0;
402 }
403 
404 /* Note that we've entered a COND_EXPR.  */
405 
406 static void
gimple_push_condition(void)407 gimple_push_condition (void)
408 {
409 #ifdef ENABLE_GIMPLE_CHECKING
410   if (gimplify_ctxp->conditions == 0)
411     gcc_assert (gimple_seq_empty_p (gimplify_ctxp->conditional_cleanups));
412 #endif
413   ++(gimplify_ctxp->conditions);
414 }
415 
416 /* Note that we've left a COND_EXPR.  If we're back at unconditional scope
417    now, add any conditional cleanups we've seen to the prequeue.  */
418 
419 static void
gimple_pop_condition(gimple_seq * pre_p)420 gimple_pop_condition (gimple_seq *pre_p)
421 {
422   int conds = --(gimplify_ctxp->conditions);
423 
424   gcc_assert (conds >= 0);
425   if (conds == 0)
426     {
427       gimplify_seq_add_seq (pre_p, gimplify_ctxp->conditional_cleanups);
428       gimplify_ctxp->conditional_cleanups = NULL;
429     }
430 }
431 
432 /* A stable comparison routine for use with splay trees and DECLs.  */
433 
434 static int
splay_tree_compare_decl_uid(splay_tree_key xa,splay_tree_key xb)435 splay_tree_compare_decl_uid (splay_tree_key xa, splay_tree_key xb)
436 {
437   tree a = (tree) xa;
438   tree b = (tree) xb;
439 
440   return DECL_UID (a) - DECL_UID (b);
441 }
442 
443 /* Create a new omp construct that deals with variable remapping.  */
444 
445 static struct gimplify_omp_ctx *
new_omp_context(enum omp_region_type region_type)446 new_omp_context (enum omp_region_type region_type)
447 {
448   struct gimplify_omp_ctx *c;
449 
450   c = XCNEW (struct gimplify_omp_ctx);
451   c->outer_context = gimplify_omp_ctxp;
452   c->variables = splay_tree_new (splay_tree_compare_decl_uid, 0, 0);
453   c->privatized_types = new hash_set<tree>;
454   c->location = input_location;
455   c->region_type = region_type;
456   if ((region_type & ORT_TASK) == 0)
457     c->default_kind = OMP_CLAUSE_DEFAULT_SHARED;
458   else
459     c->default_kind = OMP_CLAUSE_DEFAULT_UNSPECIFIED;
460   c->defaultmap[GDMK_SCALAR] = GOVD_MAP;
461   c->defaultmap[GDMK_AGGREGATE] = GOVD_MAP;
462   c->defaultmap[GDMK_ALLOCATABLE] = GOVD_MAP;
463   c->defaultmap[GDMK_POINTER] = GOVD_MAP;
464 
465   return c;
466 }
467 
468 /* Destroy an omp construct that deals with variable remapping.  */
469 
470 static void
delete_omp_context(struct gimplify_omp_ctx * c)471 delete_omp_context (struct gimplify_omp_ctx *c)
472 {
473   splay_tree_delete (c->variables);
474   delete c->privatized_types;
475   c->loop_iter_var.release ();
476   XDELETE (c);
477 }
478 
479 static void omp_add_variable (struct gimplify_omp_ctx *, tree, unsigned int);
480 static bool omp_notice_variable (struct gimplify_omp_ctx *, tree, bool);
481 
482 /* Both gimplify the statement T and append it to *SEQ_P.  This function
483    behaves exactly as gimplify_stmt, but you don't have to pass T as a
484    reference.  */
485 
486 void
gimplify_and_add(tree t,gimple_seq * seq_p)487 gimplify_and_add (tree t, gimple_seq *seq_p)
488 {
489   gimplify_stmt (&t, seq_p);
490 }
491 
492 /* Gimplify statement T into sequence *SEQ_P, and return the first
493    tuple in the sequence of generated tuples for this statement.
494    Return NULL if gimplifying T produced no tuples.  */
495 
496 static gimple *
gimplify_and_return_first(tree t,gimple_seq * seq_p)497 gimplify_and_return_first (tree t, gimple_seq *seq_p)
498 {
499   gimple_stmt_iterator last = gsi_last (*seq_p);
500 
501   gimplify_and_add (t, seq_p);
502 
503   if (!gsi_end_p (last))
504     {
505       gsi_next (&last);
506       return gsi_stmt (last);
507     }
508   else
509     return gimple_seq_first_stmt (*seq_p);
510 }
511 
512 /* Returns true iff T is a valid RHS for an assignment to an un-renamed
513    LHS, or for a call argument.  */
514 
515 static bool
is_gimple_mem_rhs(tree t)516 is_gimple_mem_rhs (tree t)
517 {
518   /* If we're dealing with a renamable type, either source or dest must be
519      a renamed variable.  */
520   if (is_gimple_reg_type (TREE_TYPE (t)))
521     return is_gimple_val (t);
522   else
523     return is_gimple_val (t) || is_gimple_lvalue (t);
524 }
525 
526 /* Return true if T is a CALL_EXPR or an expression that can be
527    assigned to a temporary.  Note that this predicate should only be
528    used during gimplification.  See the rationale for this in
529    gimplify_modify_expr.  */
530 
531 static bool
is_gimple_reg_rhs_or_call(tree t)532 is_gimple_reg_rhs_or_call (tree t)
533 {
534   return (get_gimple_rhs_class (TREE_CODE (t)) != GIMPLE_INVALID_RHS
535 	  || TREE_CODE (t) == CALL_EXPR);
536 }
537 
538 /* Return true if T is a valid memory RHS or a CALL_EXPR.  Note that
539    this predicate should only be used during gimplification.  See the
540    rationale for this in gimplify_modify_expr.  */
541 
542 static bool
is_gimple_mem_rhs_or_call(tree t)543 is_gimple_mem_rhs_or_call (tree t)
544 {
545   /* If we're dealing with a renamable type, either source or dest must be
546      a renamed variable.  */
547   if (is_gimple_reg_type (TREE_TYPE (t)))
548     return is_gimple_val (t);
549   else
550     return (is_gimple_val (t)
551 	    || is_gimple_lvalue (t)
552 	    || TREE_CLOBBER_P (t)
553 	    || TREE_CODE (t) == CALL_EXPR);
554 }
555 
556 /* Create a temporary with a name derived from VAL.  Subroutine of
557    lookup_tmp_var; nobody else should call this function.  */
558 
559 static inline tree
create_tmp_from_val(tree val)560 create_tmp_from_val (tree val)
561 {
562   /* Drop all qualifiers and address-space information from the value type.  */
563   tree type = TYPE_MAIN_VARIANT (TREE_TYPE (val));
564   tree var = create_tmp_var (type, get_name (val));
565   return var;
566 }
567 
568 /* Create a temporary to hold the value of VAL.  If IS_FORMAL, try to reuse
569    an existing expression temporary.  */
570 
571 static tree
lookup_tmp_var(tree val,bool is_formal)572 lookup_tmp_var (tree val, bool is_formal)
573 {
574   tree ret;
575 
576   /* If not optimizing, never really reuse a temporary.  local-alloc
577      won't allocate any variable that is used in more than one basic
578      block, which means it will go into memory, causing much extra
579      work in reload and final and poorer code generation, outweighing
580      the extra memory allocation here.  */
581   if (!optimize || !is_formal || TREE_SIDE_EFFECTS (val))
582     ret = create_tmp_from_val (val);
583   else
584     {
585       elt_t elt, *elt_p;
586       elt_t **slot;
587 
588       elt.val = val;
589       if (!gimplify_ctxp->temp_htab)
590         gimplify_ctxp->temp_htab = new hash_table<gimplify_hasher> (1000);
591       slot = gimplify_ctxp->temp_htab->find_slot (&elt, INSERT);
592       if (*slot == NULL)
593 	{
594 	  elt_p = XNEW (elt_t);
595 	  elt_p->val = val;
596 	  elt_p->temp = ret = create_tmp_from_val (val);
597 	  *slot = elt_p;
598 	}
599       else
600 	{
601 	  elt_p = *slot;
602           ret = elt_p->temp;
603 	}
604     }
605 
606   return ret;
607 }
608 
609 /* Helper for get_formal_tmp_var and get_initialized_tmp_var.  */
610 
611 static tree
internal_get_tmp_var(tree val,gimple_seq * pre_p,gimple_seq * post_p,bool is_formal,bool allow_ssa)612 internal_get_tmp_var (tree val, gimple_seq *pre_p, gimple_seq *post_p,
613                       bool is_formal, bool allow_ssa)
614 {
615   tree t, mod;
616 
617   /* Notice that we explicitly allow VAL to be a CALL_EXPR so that we
618      can create an INIT_EXPR and convert it into a GIMPLE_CALL below.  */
619   gimplify_expr (&val, pre_p, post_p, is_gimple_reg_rhs_or_call,
620 		 fb_rvalue);
621 
622   if (allow_ssa
623       && gimplify_ctxp->into_ssa
624       && is_gimple_reg_type (TREE_TYPE (val)))
625     {
626       t = make_ssa_name (TYPE_MAIN_VARIANT (TREE_TYPE (val)));
627       if (! gimple_in_ssa_p (cfun))
628 	{
629 	  const char *name = get_name (val);
630 	  if (name)
631 	    SET_SSA_NAME_VAR_OR_IDENTIFIER (t, create_tmp_var_name (name));
632 	}
633     }
634   else
635     t = lookup_tmp_var (val, is_formal);
636 
637   mod = build2 (INIT_EXPR, TREE_TYPE (t), t, unshare_expr (val));
638 
639   SET_EXPR_LOCATION (mod, EXPR_LOC_OR_LOC (val, input_location));
640 
641   /* gimplify_modify_expr might want to reduce this further.  */
642   gimplify_and_add (mod, pre_p);
643   ggc_free (mod);
644 
645   return t;
646 }
647 
648 /* Return a formal temporary variable initialized with VAL.  PRE_P is as
649    in gimplify_expr.  Only use this function if:
650 
651    1) The value of the unfactored expression represented by VAL will not
652       change between the initialization and use of the temporary, and
653    2) The temporary will not be otherwise modified.
654 
655    For instance, #1 means that this is inappropriate for SAVE_EXPR temps,
656    and #2 means it is inappropriate for && temps.
657 
658    For other cases, use get_initialized_tmp_var instead.  */
659 
660 tree
get_formal_tmp_var(tree val,gimple_seq * pre_p)661 get_formal_tmp_var (tree val, gimple_seq *pre_p)
662 {
663   return internal_get_tmp_var (val, pre_p, NULL, true, true);
664 }
665 
666 /* Return a temporary variable initialized with VAL.  PRE_P and POST_P
667    are as in gimplify_expr.  */
668 
669 tree
get_initialized_tmp_var(tree val,gimple_seq * pre_p,gimple_seq * post_p,bool allow_ssa)670 get_initialized_tmp_var (tree val, gimple_seq *pre_p,
671 			 gimple_seq *post_p /* = NULL */,
672 			 bool allow_ssa /* = true */)
673 {
674   return internal_get_tmp_var (val, pre_p, post_p, false, allow_ssa);
675 }
676 
677 /* Declare all the variables in VARS in SCOPE.  If DEBUG_INFO is true,
678    generate debug info for them; otherwise don't.  */
679 
680 void
declare_vars(tree vars,gimple * gs,bool debug_info)681 declare_vars (tree vars, gimple *gs, bool debug_info)
682 {
683   tree last = vars;
684   if (last)
685     {
686       tree temps, block;
687 
688       gbind *scope = as_a <gbind *> (gs);
689 
690       temps = nreverse (last);
691 
692       block = gimple_bind_block (scope);
693       gcc_assert (!block || TREE_CODE (block) == BLOCK);
694       if (!block || !debug_info)
695 	{
696 	  DECL_CHAIN (last) = gimple_bind_vars (scope);
697 	  gimple_bind_set_vars (scope, temps);
698 	}
699       else
700 	{
701 	  /* We need to attach the nodes both to the BIND_EXPR and to its
702 	     associated BLOCK for debugging purposes.  The key point here
703 	     is that the BLOCK_VARS of the BIND_EXPR_BLOCK of a BIND_EXPR
704 	     is a subchain of the BIND_EXPR_VARS of the BIND_EXPR.  */
705 	  if (BLOCK_VARS (block))
706 	    BLOCK_VARS (block) = chainon (BLOCK_VARS (block), temps);
707 	  else
708 	    {
709 	      gimple_bind_set_vars (scope,
710 	      			    chainon (gimple_bind_vars (scope), temps));
711 	      BLOCK_VARS (block) = temps;
712 	    }
713 	}
714     }
715 }
716 
717 /* For VAR a VAR_DECL of variable size, try to find a constant upper bound
718    for the size and adjust DECL_SIZE/DECL_SIZE_UNIT accordingly.  Abort if
719    no such upper bound can be obtained.  */
720 
721 static void
force_constant_size(tree var)722 force_constant_size (tree var)
723 {
724   /* The only attempt we make is by querying the maximum size of objects
725      of the variable's type.  */
726 
727   HOST_WIDE_INT max_size;
728 
729   gcc_assert (VAR_P (var));
730 
731   max_size = max_int_size_in_bytes (TREE_TYPE (var));
732 
733   gcc_assert (max_size >= 0);
734 
735   DECL_SIZE_UNIT (var)
736     = build_int_cst (TREE_TYPE (DECL_SIZE_UNIT (var)), max_size);
737   DECL_SIZE (var)
738     = build_int_cst (TREE_TYPE (DECL_SIZE (var)), max_size * BITS_PER_UNIT);
739 }
740 
741 /* Push the temporary variable TMP into the current binding.  */
742 
743 void
gimple_add_tmp_var_fn(struct function * fn,tree tmp)744 gimple_add_tmp_var_fn (struct function *fn, tree tmp)
745 {
746   gcc_assert (!DECL_CHAIN (tmp) && !DECL_SEEN_IN_BIND_EXPR_P (tmp));
747 
748   /* Later processing assumes that the object size is constant, which might
749      not be true at this point.  Force the use of a constant upper bound in
750      this case.  */
751   if (!tree_fits_poly_uint64_p (DECL_SIZE_UNIT (tmp)))
752     force_constant_size (tmp);
753 
754   DECL_CONTEXT (tmp) = fn->decl;
755   DECL_SEEN_IN_BIND_EXPR_P (tmp) = 1;
756 
757   record_vars_into (tmp, fn->decl);
758 }
759 
760 /* Push the temporary variable TMP into the current binding.  */
761 
762 void
gimple_add_tmp_var(tree tmp)763 gimple_add_tmp_var (tree tmp)
764 {
765   gcc_assert (!DECL_CHAIN (tmp) && !DECL_SEEN_IN_BIND_EXPR_P (tmp));
766 
767   /* Later processing assumes that the object size is constant, which might
768      not be true at this point.  Force the use of a constant upper bound in
769      this case.  */
770   if (!tree_fits_poly_uint64_p (DECL_SIZE_UNIT (tmp)))
771     force_constant_size (tmp);
772 
773   DECL_CONTEXT (tmp) = current_function_decl;
774   DECL_SEEN_IN_BIND_EXPR_P (tmp) = 1;
775 
776   if (gimplify_ctxp)
777     {
778       DECL_CHAIN (tmp) = gimplify_ctxp->temps;
779       gimplify_ctxp->temps = tmp;
780 
781       /* Mark temporaries local within the nearest enclosing parallel.  */
782       if (gimplify_omp_ctxp)
783 	{
784 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
785 	  int flag = GOVD_LOCAL | GOVD_SEEN;
786 	  while (ctx
787 		 && (ctx->region_type == ORT_WORKSHARE
788 		     || ctx->region_type == ORT_TASKGROUP
789 		     || ctx->region_type == ORT_SIMD
790 		     || ctx->region_type == ORT_ACC))
791 	    {
792 	      if (ctx->region_type == ORT_SIMD
793 		  && TREE_ADDRESSABLE (tmp)
794 		  && !TREE_STATIC (tmp))
795 		{
796 		  if (TREE_CODE (DECL_SIZE_UNIT (tmp)) != INTEGER_CST)
797 		    ctx->add_safelen1 = true;
798 		  else if (ctx->in_for_exprs)
799 		    flag = GOVD_PRIVATE;
800 		  else
801 		    flag = GOVD_PRIVATE | GOVD_SEEN;
802 		  break;
803 		}
804 	      ctx = ctx->outer_context;
805 	    }
806 	  if (ctx)
807 	    omp_add_variable (ctx, tmp, flag);
808 	}
809     }
810   else if (cfun)
811     record_vars (tmp);
812   else
813     {
814       gimple_seq body_seq;
815 
816       /* This case is for nested functions.  We need to expose the locals
817 	 they create.  */
818       body_seq = gimple_body (current_function_decl);
819       declare_vars (tmp, gimple_seq_first_stmt (body_seq), false);
820     }
821 }
822 
823 
824 
825 /* This page contains routines to unshare tree nodes, i.e. to duplicate tree
826    nodes that are referenced more than once in GENERIC functions.  This is
827    necessary because gimplification (translation into GIMPLE) is performed
828    by modifying tree nodes in-place, so gimplication of a shared node in a
829    first context could generate an invalid GIMPLE form in a second context.
830 
831    This is achieved with a simple mark/copy/unmark algorithm that walks the
832    GENERIC representation top-down, marks nodes with TREE_VISITED the first
833    time it encounters them, duplicates them if they already have TREE_VISITED
834    set, and finally removes the TREE_VISITED marks it has set.
835 
836    The algorithm works only at the function level, i.e. it generates a GENERIC
837    representation of a function with no nodes shared within the function when
838    passed a GENERIC function (except for nodes that are allowed to be shared).
839 
840    At the global level, it is also necessary to unshare tree nodes that are
841    referenced in more than one function, for the same aforementioned reason.
842    This requires some cooperation from the front-end.  There are 2 strategies:
843 
844      1. Manual unsharing.  The front-end needs to call unshare_expr on every
845         expression that might end up being shared across functions.
846 
847      2. Deep unsharing.  This is an extension of regular unsharing.  Instead
848         of calling unshare_expr on expressions that might be shared across
849         functions, the front-end pre-marks them with TREE_VISITED.  This will
850         ensure that they are unshared on the first reference within functions
851         when the regular unsharing algorithm runs.  The counterpart is that
852         this algorithm must look deeper than for manual unsharing, which is
853         specified by LANG_HOOKS_DEEP_UNSHARING.
854 
855   If there are only few specific cases of node sharing across functions, it is
856   probably easier for a front-end to unshare the expressions manually.  On the
857   contrary, if the expressions generated at the global level are as widespread
858   as expressions generated within functions, deep unsharing is very likely the
859   way to go.  */
860 
861 /* Similar to copy_tree_r but do not copy SAVE_EXPR or TARGET_EXPR nodes.
862    These nodes model computations that must be done once.  If we were to
863    unshare something like SAVE_EXPR(i++), the gimplification process would
864    create wrong code.  However, if DATA is non-null, it must hold a pointer
865    set that is used to unshare the subtrees of these nodes.  */
866 
867 static tree
mostly_copy_tree_r(tree * tp,int * walk_subtrees,void * data)868 mostly_copy_tree_r (tree *tp, int *walk_subtrees, void *data)
869 {
870   tree t = *tp;
871   enum tree_code code = TREE_CODE (t);
872 
873   /* Do not copy SAVE_EXPR, TARGET_EXPR or BIND_EXPR nodes themselves, but
874      copy their subtrees if we can make sure to do it only once.  */
875   if (code == SAVE_EXPR || code == TARGET_EXPR || code == BIND_EXPR)
876     {
877       if (data && !((hash_set<tree> *)data)->add (t))
878 	;
879       else
880 	*walk_subtrees = 0;
881     }
882 
883   /* Stop at types, decls, constants like copy_tree_r.  */
884   else if (TREE_CODE_CLASS (code) == tcc_type
885 	   || TREE_CODE_CLASS (code) == tcc_declaration
886 	   || TREE_CODE_CLASS (code) == tcc_constant)
887     *walk_subtrees = 0;
888 
889   /* Cope with the statement expression extension.  */
890   else if (code == STATEMENT_LIST)
891     ;
892 
893   /* Leave the bulk of the work to copy_tree_r itself.  */
894   else
895     copy_tree_r (tp, walk_subtrees, NULL);
896 
897   return NULL_TREE;
898 }
899 
900 /* Callback for walk_tree to unshare most of the shared trees rooted at *TP.
901    If *TP has been visited already, then *TP is deeply copied by calling
902    mostly_copy_tree_r.  DATA is passed to mostly_copy_tree_r unmodified.  */
903 
904 static tree
copy_if_shared_r(tree * tp,int * walk_subtrees,void * data)905 copy_if_shared_r (tree *tp, int *walk_subtrees, void *data)
906 {
907   tree t = *tp;
908   enum tree_code code = TREE_CODE (t);
909 
910   /* Skip types, decls, and constants.  But we do want to look at their
911      types and the bounds of types.  Mark them as visited so we properly
912      unmark their subtrees on the unmark pass.  If we've already seen them,
913      don't look down further.  */
914   if (TREE_CODE_CLASS (code) == tcc_type
915       || TREE_CODE_CLASS (code) == tcc_declaration
916       || TREE_CODE_CLASS (code) == tcc_constant)
917     {
918       if (TREE_VISITED (t))
919 	*walk_subtrees = 0;
920       else
921 	TREE_VISITED (t) = 1;
922     }
923 
924   /* If this node has been visited already, unshare it and don't look
925      any deeper.  */
926   else if (TREE_VISITED (t))
927     {
928       walk_tree (tp, mostly_copy_tree_r, data, NULL);
929       *walk_subtrees = 0;
930     }
931 
932   /* Otherwise, mark the node as visited and keep looking.  */
933   else
934     TREE_VISITED (t) = 1;
935 
936   return NULL_TREE;
937 }
938 
939 /* Unshare most of the shared trees rooted at *TP.  DATA is passed to the
940    copy_if_shared_r callback unmodified.  */
941 
942 void
copy_if_shared(tree * tp,void * data)943 copy_if_shared (tree *tp, void *data)
944 {
945   walk_tree (tp, copy_if_shared_r, data, NULL);
946 }
947 
948 /* Unshare all the trees in the body of FNDECL, as well as in the bodies of
949    any nested functions.  */
950 
951 static void
unshare_body(tree fndecl)952 unshare_body (tree fndecl)
953 {
954   struct cgraph_node *cgn = cgraph_node::get (fndecl);
955   /* If the language requires deep unsharing, we need a pointer set to make
956      sure we don't repeatedly unshare subtrees of unshareable nodes.  */
957   hash_set<tree> *visited
958     = lang_hooks.deep_unsharing ? new hash_set<tree> : NULL;
959 
960   copy_if_shared (&DECL_SAVED_TREE (fndecl), visited);
961   copy_if_shared (&DECL_SIZE (DECL_RESULT (fndecl)), visited);
962   copy_if_shared (&DECL_SIZE_UNIT (DECL_RESULT (fndecl)), visited);
963 
964   delete visited;
965 
966   if (cgn)
967     for (cgn = first_nested_function (cgn); cgn;
968 	 cgn = next_nested_function (cgn))
969       unshare_body (cgn->decl);
970 }
971 
972 /* Callback for walk_tree to unmark the visited trees rooted at *TP.
973    Subtrees are walked until the first unvisited node is encountered.  */
974 
975 static tree
unmark_visited_r(tree * tp,int * walk_subtrees,void * data ATTRIBUTE_UNUSED)976 unmark_visited_r (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
977 {
978   tree t = *tp;
979 
980   /* If this node has been visited, unmark it and keep looking.  */
981   if (TREE_VISITED (t))
982     TREE_VISITED (t) = 0;
983 
984   /* Otherwise, don't look any deeper.  */
985   else
986     *walk_subtrees = 0;
987 
988   return NULL_TREE;
989 }
990 
991 /* Unmark the visited trees rooted at *TP.  */
992 
993 static inline void
unmark_visited(tree * tp)994 unmark_visited (tree *tp)
995 {
996   walk_tree (tp, unmark_visited_r, NULL, NULL);
997 }
998 
999 /* Likewise, but mark all trees as not visited.  */
1000 
1001 static void
unvisit_body(tree fndecl)1002 unvisit_body (tree fndecl)
1003 {
1004   struct cgraph_node *cgn = cgraph_node::get (fndecl);
1005 
1006   unmark_visited (&DECL_SAVED_TREE (fndecl));
1007   unmark_visited (&DECL_SIZE (DECL_RESULT (fndecl)));
1008   unmark_visited (&DECL_SIZE_UNIT (DECL_RESULT (fndecl)));
1009 
1010   if (cgn)
1011     for (cgn = first_nested_function (cgn);
1012 	 cgn; cgn = next_nested_function (cgn))
1013       unvisit_body (cgn->decl);
1014 }
1015 
1016 /* Unconditionally make an unshared copy of EXPR.  This is used when using
1017    stored expressions which span multiple functions, such as BINFO_VTABLE,
1018    as the normal unsharing process can't tell that they're shared.  */
1019 
1020 tree
unshare_expr(tree expr)1021 unshare_expr (tree expr)
1022 {
1023   walk_tree (&expr, mostly_copy_tree_r, NULL, NULL);
1024   return expr;
1025 }
1026 
1027 /* Worker for unshare_expr_without_location.  */
1028 
1029 static tree
prune_expr_location(tree * tp,int * walk_subtrees,void *)1030 prune_expr_location (tree *tp, int *walk_subtrees, void *)
1031 {
1032   if (EXPR_P (*tp))
1033     SET_EXPR_LOCATION (*tp, UNKNOWN_LOCATION);
1034   else
1035     *walk_subtrees = 0;
1036   return NULL_TREE;
1037 }
1038 
1039 /* Similar to unshare_expr but also prune all expression locations
1040    from EXPR.  */
1041 
1042 tree
unshare_expr_without_location(tree expr)1043 unshare_expr_without_location (tree expr)
1044 {
1045   walk_tree (&expr, mostly_copy_tree_r, NULL, NULL);
1046   if (EXPR_P (expr))
1047     walk_tree (&expr, prune_expr_location, NULL, NULL);
1048   return expr;
1049 }
1050 
1051 /* Return the EXPR_LOCATION of EXPR, if it (maybe recursively) has
1052    one, OR_ELSE otherwise.  The location of a STATEMENT_LISTs
1053    comprising at least one DEBUG_BEGIN_STMT followed by exactly one
1054    EXPR is the location of the EXPR.  */
1055 
1056 static location_t
1057 rexpr_location (tree expr, location_t or_else = UNKNOWN_LOCATION)
1058 {
1059   if (!expr)
1060     return or_else;
1061 
1062   if (EXPR_HAS_LOCATION (expr))
1063     return EXPR_LOCATION (expr);
1064 
1065   if (TREE_CODE (expr) != STATEMENT_LIST)
1066     return or_else;
1067 
1068   tree_stmt_iterator i = tsi_start (expr);
1069 
1070   bool found = false;
1071   while (!tsi_end_p (i) && TREE_CODE (tsi_stmt (i)) == DEBUG_BEGIN_STMT)
1072     {
1073       found = true;
1074       tsi_next (&i);
1075     }
1076 
1077   if (!found || !tsi_one_before_end_p (i))
1078     return or_else;
1079 
1080   return rexpr_location (tsi_stmt (i), or_else);
1081 }
1082 
1083 /* Return TRUE iff EXPR (maybe recursively) has a location; see
1084    rexpr_location for the potential recursion.  */
1085 
1086 static inline bool
rexpr_has_location(tree expr)1087 rexpr_has_location (tree expr)
1088 {
1089   return rexpr_location (expr) != UNKNOWN_LOCATION;
1090 }
1091 
1092 
1093 /* WRAPPER is a code such as BIND_EXPR or CLEANUP_POINT_EXPR which can both
1094    contain statements and have a value.  Assign its value to a temporary
1095    and give it void_type_node.  Return the temporary, or NULL_TREE if
1096    WRAPPER was already void.  */
1097 
1098 tree
voidify_wrapper_expr(tree wrapper,tree temp)1099 voidify_wrapper_expr (tree wrapper, tree temp)
1100 {
1101   tree type = TREE_TYPE (wrapper);
1102   if (type && !VOID_TYPE_P (type))
1103     {
1104       tree *p;
1105 
1106       /* Set p to point to the body of the wrapper.  Loop until we find
1107 	 something that isn't a wrapper.  */
1108       for (p = &wrapper; p && *p; )
1109 	{
1110 	  switch (TREE_CODE (*p))
1111 	    {
1112 	    case BIND_EXPR:
1113 	      TREE_SIDE_EFFECTS (*p) = 1;
1114 	      TREE_TYPE (*p) = void_type_node;
1115 	      /* For a BIND_EXPR, the body is operand 1.  */
1116 	      p = &BIND_EXPR_BODY (*p);
1117 	      break;
1118 
1119 	    case CLEANUP_POINT_EXPR:
1120 	    case TRY_FINALLY_EXPR:
1121 	    case TRY_CATCH_EXPR:
1122 	      TREE_SIDE_EFFECTS (*p) = 1;
1123 	      TREE_TYPE (*p) = void_type_node;
1124 	      p = &TREE_OPERAND (*p, 0);
1125 	      break;
1126 
1127 	    case STATEMENT_LIST:
1128 	      {
1129 		tree_stmt_iterator i = tsi_last (*p);
1130 		TREE_SIDE_EFFECTS (*p) = 1;
1131 		TREE_TYPE (*p) = void_type_node;
1132 		p = tsi_end_p (i) ? NULL : tsi_stmt_ptr (i);
1133 	      }
1134 	      break;
1135 
1136 	    case COMPOUND_EXPR:
1137 	      /* Advance to the last statement.  Set all container types to
1138 		 void.  */
1139 	      for (; TREE_CODE (*p) == COMPOUND_EXPR; p = &TREE_OPERAND (*p, 1))
1140 		{
1141 		  TREE_SIDE_EFFECTS (*p) = 1;
1142 		  TREE_TYPE (*p) = void_type_node;
1143 		}
1144 	      break;
1145 
1146 	    case TRANSACTION_EXPR:
1147 	      TREE_SIDE_EFFECTS (*p) = 1;
1148 	      TREE_TYPE (*p) = void_type_node;
1149 	      p = &TRANSACTION_EXPR_BODY (*p);
1150 	      break;
1151 
1152 	    default:
1153 	      /* Assume that any tree upon which voidify_wrapper_expr is
1154 		 directly called is a wrapper, and that its body is op0.  */
1155 	      if (p == &wrapper)
1156 		{
1157 		  TREE_SIDE_EFFECTS (*p) = 1;
1158 		  TREE_TYPE (*p) = void_type_node;
1159 		  p = &TREE_OPERAND (*p, 0);
1160 		  break;
1161 		}
1162 	      goto out;
1163 	    }
1164 	}
1165 
1166     out:
1167       if (p == NULL || IS_EMPTY_STMT (*p))
1168 	temp = NULL_TREE;
1169       else if (temp)
1170 	{
1171 	  /* The wrapper is on the RHS of an assignment that we're pushing
1172 	     down.  */
1173 	  gcc_assert (TREE_CODE (temp) == INIT_EXPR
1174 		      || TREE_CODE (temp) == MODIFY_EXPR);
1175 	  TREE_OPERAND (temp, 1) = *p;
1176 	  *p = temp;
1177 	}
1178       else
1179 	{
1180 	  temp = create_tmp_var (type, "retval");
1181 	  *p = build2 (INIT_EXPR, type, temp, *p);
1182 	}
1183 
1184       return temp;
1185     }
1186 
1187   return NULL_TREE;
1188 }
1189 
1190 /* Prepare calls to builtins to SAVE and RESTORE the stack as well as
1191    a temporary through which they communicate.  */
1192 
1193 static void
build_stack_save_restore(gcall ** save,gcall ** restore)1194 build_stack_save_restore (gcall **save, gcall **restore)
1195 {
1196   tree tmp_var;
1197 
1198   *save = gimple_build_call (builtin_decl_implicit (BUILT_IN_STACK_SAVE), 0);
1199   tmp_var = create_tmp_var (ptr_type_node, "saved_stack");
1200   gimple_call_set_lhs (*save, tmp_var);
1201 
1202   *restore
1203     = gimple_build_call (builtin_decl_implicit (BUILT_IN_STACK_RESTORE),
1204 			 1, tmp_var);
1205 }
1206 
1207 /* Generate IFN_ASAN_MARK call that poisons shadow of a for DECL variable.  */
1208 
1209 static tree
build_asan_poison_call_expr(tree decl)1210 build_asan_poison_call_expr (tree decl)
1211 {
1212   /* Do not poison variables that have size equal to zero.  */
1213   tree unit_size = DECL_SIZE_UNIT (decl);
1214   if (zerop (unit_size))
1215     return NULL_TREE;
1216 
1217   tree base = build_fold_addr_expr (decl);
1218 
1219   return build_call_expr_internal_loc (UNKNOWN_LOCATION, IFN_ASAN_MARK,
1220 				       void_type_node, 3,
1221 				       build_int_cst (integer_type_node,
1222 						      ASAN_MARK_POISON),
1223 				       base, unit_size);
1224 }
1225 
1226 /* Generate IFN_ASAN_MARK call that would poison or unpoison, depending
1227    on POISON flag, shadow memory of a DECL variable.  The call will be
1228    put on location identified by IT iterator, where BEFORE flag drives
1229    position where the stmt will be put.  */
1230 
1231 static void
asan_poison_variable(tree decl,bool poison,gimple_stmt_iterator * it,bool before)1232 asan_poison_variable (tree decl, bool poison, gimple_stmt_iterator *it,
1233 		      bool before)
1234 {
1235   tree unit_size = DECL_SIZE_UNIT (decl);
1236   tree base = build_fold_addr_expr (decl);
1237 
1238   /* Do not poison variables that have size equal to zero.  */
1239   if (zerop (unit_size))
1240     return;
1241 
1242   /* It's necessary to have all stack variables aligned to ASAN granularity
1243      bytes.  */
1244   gcc_assert (!hwasan_sanitize_p () || hwasan_sanitize_stack_p ());
1245   unsigned shadow_granularity
1246     = hwasan_sanitize_p () ? HWASAN_TAG_GRANULE_SIZE : ASAN_SHADOW_GRANULARITY;
1247   if (DECL_ALIGN_UNIT (decl) <= shadow_granularity)
1248     SET_DECL_ALIGN (decl, BITS_PER_UNIT * shadow_granularity);
1249 
1250   HOST_WIDE_INT flags = poison ? ASAN_MARK_POISON : ASAN_MARK_UNPOISON;
1251 
1252   gimple *g
1253     = gimple_build_call_internal (IFN_ASAN_MARK, 3,
1254 				  build_int_cst (integer_type_node, flags),
1255 				  base, unit_size);
1256 
1257   if (before)
1258     gsi_insert_before (it, g, GSI_NEW_STMT);
1259   else
1260     gsi_insert_after (it, g, GSI_NEW_STMT);
1261 }
1262 
1263 /* Generate IFN_ASAN_MARK internal call that depending on POISON flag
1264    either poisons or unpoisons a DECL.  Created statement is appended
1265    to SEQ_P gimple sequence.  */
1266 
1267 static void
asan_poison_variable(tree decl,bool poison,gimple_seq * seq_p)1268 asan_poison_variable (tree decl, bool poison, gimple_seq *seq_p)
1269 {
1270   gimple_stmt_iterator it = gsi_last (*seq_p);
1271   bool before = false;
1272 
1273   if (gsi_end_p (it))
1274     before = true;
1275 
1276   asan_poison_variable (decl, poison, &it, before);
1277 }
1278 
1279 /* Sort pair of VAR_DECLs A and B by DECL_UID.  */
1280 
1281 static int
sort_by_decl_uid(const void * a,const void * b)1282 sort_by_decl_uid (const void *a, const void *b)
1283 {
1284   const tree *t1 = (const tree *)a;
1285   const tree *t2 = (const tree *)b;
1286 
1287   int uid1 = DECL_UID (*t1);
1288   int uid2 = DECL_UID (*t2);
1289 
1290   if (uid1 < uid2)
1291     return -1;
1292   else if (uid1 > uid2)
1293     return 1;
1294   else
1295     return 0;
1296 }
1297 
1298 /* Generate IFN_ASAN_MARK internal call for all VARIABLES
1299    depending on POISON flag.  Created statement is appended
1300    to SEQ_P gimple sequence.  */
1301 
1302 static void
asan_poison_variables(hash_set<tree> * variables,bool poison,gimple_seq * seq_p)1303 asan_poison_variables (hash_set<tree> *variables, bool poison, gimple_seq *seq_p)
1304 {
1305   unsigned c = variables->elements ();
1306   if (c == 0)
1307     return;
1308 
1309   auto_vec<tree> sorted_variables (c);
1310 
1311   for (hash_set<tree>::iterator it = variables->begin ();
1312        it != variables->end (); ++it)
1313     sorted_variables.safe_push (*it);
1314 
1315   sorted_variables.qsort (sort_by_decl_uid);
1316 
1317   unsigned i;
1318   tree var;
1319   FOR_EACH_VEC_ELT (sorted_variables, i, var)
1320     {
1321       asan_poison_variable (var, poison, seq_p);
1322 
1323       /* Add use_after_scope_memory attribute for the variable in order
1324 	 to prevent re-written into SSA.  */
1325       if (!lookup_attribute (ASAN_USE_AFTER_SCOPE_ATTRIBUTE,
1326 			     DECL_ATTRIBUTES (var)))
1327 	DECL_ATTRIBUTES (var)
1328 	  = tree_cons (get_identifier (ASAN_USE_AFTER_SCOPE_ATTRIBUTE),
1329 		       integer_one_node,
1330 		       DECL_ATTRIBUTES (var));
1331     }
1332 }
1333 
1334 /* Gimplify a BIND_EXPR.  Just voidify and recurse.  */
1335 
1336 static enum gimplify_status
gimplify_bind_expr(tree * expr_p,gimple_seq * pre_p)1337 gimplify_bind_expr (tree *expr_p, gimple_seq *pre_p)
1338 {
1339   tree bind_expr = *expr_p;
1340   bool old_keep_stack = gimplify_ctxp->keep_stack;
1341   bool old_save_stack = gimplify_ctxp->save_stack;
1342   tree t;
1343   gbind *bind_stmt;
1344   gimple_seq body, cleanup;
1345   gcall *stack_save;
1346   location_t start_locus = 0, end_locus = 0;
1347   tree ret_clauses = NULL;
1348 
1349   tree temp = voidify_wrapper_expr (bind_expr, NULL);
1350 
1351   /* Mark variables seen in this bind expr.  */
1352   for (t = BIND_EXPR_VARS (bind_expr); t ; t = DECL_CHAIN (t))
1353     {
1354       if (VAR_P (t))
1355 	{
1356 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
1357 
1358 	  /* Mark variable as local.  */
1359 	  if (ctx && ctx->region_type != ORT_NONE && !DECL_EXTERNAL (t))
1360 	    {
1361 	      if (! DECL_SEEN_IN_BIND_EXPR_P (t)
1362 		  || splay_tree_lookup (ctx->variables,
1363 					(splay_tree_key) t) == NULL)
1364 		{
1365 		  int flag = GOVD_LOCAL;
1366 		  if (ctx->region_type == ORT_SIMD
1367 		      && TREE_ADDRESSABLE (t)
1368 		      && !TREE_STATIC (t))
1369 		    {
1370 		      if (TREE_CODE (DECL_SIZE_UNIT (t)) != INTEGER_CST)
1371 			ctx->add_safelen1 = true;
1372 		      else
1373 			flag = GOVD_PRIVATE;
1374 		    }
1375 		  omp_add_variable (ctx, t, flag | GOVD_SEEN);
1376 		}
1377 	      /* Static locals inside of target construct or offloaded
1378 		 routines need to be "omp declare target".  */
1379 	      if (TREE_STATIC (t))
1380 		for (; ctx; ctx = ctx->outer_context)
1381 		  if ((ctx->region_type & ORT_TARGET) != 0)
1382 		    {
1383 		      if (!lookup_attribute ("omp declare target",
1384 					     DECL_ATTRIBUTES (t)))
1385 			{
1386 			  tree id = get_identifier ("omp declare target");
1387 			  DECL_ATTRIBUTES (t)
1388 			    = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (t));
1389 			  varpool_node *node = varpool_node::get (t);
1390 			  if (node)
1391 			    {
1392 			      node->offloadable = 1;
1393 			      if (ENABLE_OFFLOADING && !DECL_EXTERNAL (t))
1394 				{
1395 				  g->have_offload = true;
1396 				  if (!in_lto_p)
1397 				    vec_safe_push (offload_vars, t);
1398 				}
1399 			    }
1400 			}
1401 		      break;
1402 		    }
1403 	    }
1404 
1405 	  DECL_SEEN_IN_BIND_EXPR_P (t) = 1;
1406 
1407 	  if (DECL_HARD_REGISTER (t) && !is_global_var (t) && cfun)
1408 	    cfun->has_local_explicit_reg_vars = true;
1409 	}
1410     }
1411 
1412   bind_stmt = gimple_build_bind (BIND_EXPR_VARS (bind_expr), NULL,
1413 				 BIND_EXPR_BLOCK (bind_expr));
1414   gimple_push_bind_expr (bind_stmt);
1415 
1416   gimplify_ctxp->keep_stack = false;
1417   gimplify_ctxp->save_stack = false;
1418 
1419   /* Gimplify the body into the GIMPLE_BIND tuple's body.  */
1420   body = NULL;
1421   gimplify_stmt (&BIND_EXPR_BODY (bind_expr), &body);
1422   gimple_bind_set_body (bind_stmt, body);
1423 
1424   /* Source location wise, the cleanup code (stack_restore and clobbers)
1425      belongs to the end of the block, so propagate what we have.  The
1426      stack_save operation belongs to the beginning of block, which we can
1427      infer from the bind_expr directly if the block has no explicit
1428      assignment.  */
1429   if (BIND_EXPR_BLOCK (bind_expr))
1430     {
1431       end_locus = BLOCK_SOURCE_END_LOCATION (BIND_EXPR_BLOCK (bind_expr));
1432       start_locus = BLOCK_SOURCE_LOCATION (BIND_EXPR_BLOCK (bind_expr));
1433     }
1434   if (start_locus == 0)
1435     start_locus = EXPR_LOCATION (bind_expr);
1436 
1437   cleanup = NULL;
1438   stack_save = NULL;
1439 
1440   /* If the code both contains VLAs and calls alloca, then we cannot reclaim
1441      the stack space allocated to the VLAs.  */
1442   if (gimplify_ctxp->save_stack && !gimplify_ctxp->keep_stack)
1443     {
1444       gcall *stack_restore;
1445 
1446       /* Save stack on entry and restore it on exit.  Add a try_finally
1447 	 block to achieve this.  */
1448       build_stack_save_restore (&stack_save, &stack_restore);
1449 
1450       gimple_set_location (stack_save, start_locus);
1451       gimple_set_location (stack_restore, end_locus);
1452 
1453       gimplify_seq_add_stmt (&cleanup, stack_restore);
1454     }
1455 
1456   /* Add clobbers for all variables that go out of scope.  */
1457   for (t = BIND_EXPR_VARS (bind_expr); t ; t = DECL_CHAIN (t))
1458     {
1459       if (VAR_P (t)
1460 	  && !is_global_var (t)
1461 	  && DECL_CONTEXT (t) == current_function_decl)
1462 	{
1463 	  if (!DECL_HARD_REGISTER (t)
1464 	      && !TREE_THIS_VOLATILE (t)
1465 	      && !DECL_HAS_VALUE_EXPR_P (t)
1466 	      /* Only care for variables that have to be in memory.  Others
1467 		 will be rewritten into SSA names, hence moved to the
1468 		 top-level.  */
1469 	      && !is_gimple_reg (t)
1470 	      && flag_stack_reuse != SR_NONE)
1471 	    {
1472 	      tree clobber = build_clobber (TREE_TYPE (t));
1473 	      gimple *clobber_stmt;
1474 	      clobber_stmt = gimple_build_assign (t, clobber);
1475 	      gimple_set_location (clobber_stmt, end_locus);
1476 	      gimplify_seq_add_stmt (&cleanup, clobber_stmt);
1477 	    }
1478 
1479 	  if (flag_openacc && oacc_declare_returns != NULL)
1480 	    {
1481 	      tree key = t;
1482 	      if (DECL_HAS_VALUE_EXPR_P (key))
1483 		{
1484 		  key = DECL_VALUE_EXPR (key);
1485 		  if (TREE_CODE (key) == INDIRECT_REF)
1486 		    key = TREE_OPERAND (key, 0);
1487 		}
1488 	      tree *c = oacc_declare_returns->get (key);
1489 	      if (c != NULL)
1490 		{
1491 		  if (ret_clauses)
1492 		    OMP_CLAUSE_CHAIN (*c) = ret_clauses;
1493 
1494 		  ret_clauses = unshare_expr (*c);
1495 
1496 		  oacc_declare_returns->remove (key);
1497 
1498 		  if (oacc_declare_returns->is_empty ())
1499 		    {
1500 		      delete oacc_declare_returns;
1501 		      oacc_declare_returns = NULL;
1502 		    }
1503 		}
1504 	    }
1505 	}
1506 
1507       if (asan_poisoned_variables != NULL
1508 	  && asan_poisoned_variables->contains (t))
1509 	{
1510 	  asan_poisoned_variables->remove (t);
1511 	  asan_poison_variable (t, true, &cleanup);
1512 	}
1513 
1514       if (gimplify_ctxp->live_switch_vars != NULL
1515 	  && gimplify_ctxp->live_switch_vars->contains (t))
1516 	gimplify_ctxp->live_switch_vars->remove (t);
1517     }
1518 
1519   if (ret_clauses)
1520     {
1521       gomp_target *stmt;
1522       gimple_stmt_iterator si = gsi_start (cleanup);
1523 
1524       stmt = gimple_build_omp_target (NULL, GF_OMP_TARGET_KIND_OACC_DECLARE,
1525 				      ret_clauses);
1526       gsi_insert_seq_before_without_update (&si, stmt, GSI_NEW_STMT);
1527     }
1528 
1529   if (cleanup)
1530     {
1531       gtry *gs;
1532       gimple_seq new_body;
1533 
1534       new_body = NULL;
1535       gs = gimple_build_try (gimple_bind_body (bind_stmt), cleanup,
1536 	  		     GIMPLE_TRY_FINALLY);
1537 
1538       if (stack_save)
1539 	gimplify_seq_add_stmt (&new_body, stack_save);
1540       gimplify_seq_add_stmt (&new_body, gs);
1541       gimple_bind_set_body (bind_stmt, new_body);
1542     }
1543 
1544   /* keep_stack propagates all the way up to the outermost BIND_EXPR.  */
1545   if (!gimplify_ctxp->keep_stack)
1546     gimplify_ctxp->keep_stack = old_keep_stack;
1547   gimplify_ctxp->save_stack = old_save_stack;
1548 
1549   gimple_pop_bind_expr ();
1550 
1551   gimplify_seq_add_stmt (pre_p, bind_stmt);
1552 
1553   if (temp)
1554     {
1555       *expr_p = temp;
1556       return GS_OK;
1557     }
1558 
1559   *expr_p = NULL_TREE;
1560   return GS_ALL_DONE;
1561 }
1562 
1563 /* Maybe add early return predict statement to PRE_P sequence.  */
1564 
1565 static void
maybe_add_early_return_predict_stmt(gimple_seq * pre_p)1566 maybe_add_early_return_predict_stmt (gimple_seq *pre_p)
1567 {
1568   /* If we are not in a conditional context, add PREDICT statement.  */
1569   if (gimple_conditional_context ())
1570     {
1571       gimple *predict = gimple_build_predict (PRED_TREE_EARLY_RETURN,
1572 					      NOT_TAKEN);
1573       gimplify_seq_add_stmt (pre_p, predict);
1574     }
1575 }
1576 
1577 /* Gimplify a RETURN_EXPR.  If the expression to be returned is not a
1578    GIMPLE value, it is assigned to a new temporary and the statement is
1579    re-written to return the temporary.
1580 
1581    PRE_P points to the sequence where side effects that must happen before
1582    STMT should be stored.  */
1583 
1584 static enum gimplify_status
gimplify_return_expr(tree stmt,gimple_seq * pre_p)1585 gimplify_return_expr (tree stmt, gimple_seq *pre_p)
1586 {
1587   greturn *ret;
1588   tree ret_expr = TREE_OPERAND (stmt, 0);
1589   tree result_decl, result;
1590 
1591   if (ret_expr == error_mark_node)
1592     return GS_ERROR;
1593 
1594   if (!ret_expr
1595       || TREE_CODE (ret_expr) == RESULT_DECL)
1596     {
1597       maybe_add_early_return_predict_stmt (pre_p);
1598       greturn *ret = gimple_build_return (ret_expr);
1599       gimple_set_no_warning (ret, TREE_NO_WARNING (stmt));
1600       gimplify_seq_add_stmt (pre_p, ret);
1601       return GS_ALL_DONE;
1602     }
1603 
1604   if (VOID_TYPE_P (TREE_TYPE (TREE_TYPE (current_function_decl))))
1605     result_decl = NULL_TREE;
1606   else if (TREE_CODE (ret_expr) == COMPOUND_EXPR)
1607     {
1608       /* Used in C++ for handling EH cleanup of the return value if a local
1609 	 cleanup throws.  Assume the front-end knows what it's doing.  */
1610       result_decl = DECL_RESULT (current_function_decl);
1611       /* But crash if we end up trying to modify ret_expr below.  */
1612       ret_expr = NULL_TREE;
1613     }
1614   else
1615     {
1616       result_decl = TREE_OPERAND (ret_expr, 0);
1617 
1618       /* See through a return by reference.  */
1619       if (TREE_CODE (result_decl) == INDIRECT_REF)
1620 	result_decl = TREE_OPERAND (result_decl, 0);
1621 
1622       gcc_assert ((TREE_CODE (ret_expr) == MODIFY_EXPR
1623 		   || TREE_CODE (ret_expr) == INIT_EXPR)
1624 		  && TREE_CODE (result_decl) == RESULT_DECL);
1625     }
1626 
1627   /* If aggregate_value_p is true, then we can return the bare RESULT_DECL.
1628      Recall that aggregate_value_p is FALSE for any aggregate type that is
1629      returned in registers.  If we're returning values in registers, then
1630      we don't want to extend the lifetime of the RESULT_DECL, particularly
1631      across another call.  In addition, for those aggregates for which
1632      hard_function_value generates a PARALLEL, we'll die during normal
1633      expansion of structure assignments; there's special code in expand_return
1634      to handle this case that does not exist in expand_expr.  */
1635   if (!result_decl)
1636     result = NULL_TREE;
1637   else if (aggregate_value_p (result_decl, TREE_TYPE (current_function_decl)))
1638     {
1639       if (!poly_int_tree_p (DECL_SIZE (result_decl)))
1640 	{
1641 	  if (!TYPE_SIZES_GIMPLIFIED (TREE_TYPE (result_decl)))
1642 	    gimplify_type_sizes (TREE_TYPE (result_decl), pre_p);
1643 	  /* Note that we don't use gimplify_vla_decl because the RESULT_DECL
1644 	     should be effectively allocated by the caller, i.e. all calls to
1645 	     this function must be subject to the Return Slot Optimization.  */
1646 	  gimplify_one_sizepos (&DECL_SIZE (result_decl), pre_p);
1647 	  gimplify_one_sizepos (&DECL_SIZE_UNIT (result_decl), pre_p);
1648 	}
1649       result = result_decl;
1650     }
1651   else if (gimplify_ctxp->return_temp)
1652     result = gimplify_ctxp->return_temp;
1653   else
1654     {
1655       result = create_tmp_reg (TREE_TYPE (result_decl));
1656 
1657       /* ??? With complex control flow (usually involving abnormal edges),
1658 	 we can wind up warning about an uninitialized value for this.  Due
1659 	 to how this variable is constructed and initialized, this is never
1660 	 true.  Give up and never warn.  */
1661       TREE_NO_WARNING (result) = 1;
1662 
1663       gimplify_ctxp->return_temp = result;
1664     }
1665 
1666   /* Smash the lhs of the MODIFY_EXPR to the temporary we plan to use.
1667      Then gimplify the whole thing.  */
1668   if (result != result_decl)
1669     TREE_OPERAND (ret_expr, 0) = result;
1670 
1671   gimplify_and_add (TREE_OPERAND (stmt, 0), pre_p);
1672 
1673   maybe_add_early_return_predict_stmt (pre_p);
1674   ret = gimple_build_return (result);
1675   gimple_set_no_warning (ret, TREE_NO_WARNING (stmt));
1676   gimplify_seq_add_stmt (pre_p, ret);
1677 
1678   return GS_ALL_DONE;
1679 }
1680 
1681 /* Gimplify a variable-length array DECL.  */
1682 
1683 static void
gimplify_vla_decl(tree decl,gimple_seq * seq_p)1684 gimplify_vla_decl (tree decl, gimple_seq *seq_p)
1685 {
1686   /* This is a variable-sized decl.  Simplify its size and mark it
1687      for deferred expansion.  */
1688   tree t, addr, ptr_type;
1689 
1690   gimplify_one_sizepos (&DECL_SIZE (decl), seq_p);
1691   gimplify_one_sizepos (&DECL_SIZE_UNIT (decl), seq_p);
1692 
1693   /* Don't mess with a DECL_VALUE_EXPR set by the front-end.  */
1694   if (DECL_HAS_VALUE_EXPR_P (decl))
1695     return;
1696 
1697   /* All occurrences of this decl in final gimplified code will be
1698      replaced by indirection.  Setting DECL_VALUE_EXPR does two
1699      things: First, it lets the rest of the gimplifier know what
1700      replacement to use.  Second, it lets the debug info know
1701      where to find the value.  */
1702   ptr_type = build_pointer_type (TREE_TYPE (decl));
1703   addr = create_tmp_var (ptr_type, get_name (decl));
1704   DECL_IGNORED_P (addr) = 0;
1705   t = build_fold_indirect_ref (addr);
1706   TREE_THIS_NOTRAP (t) = 1;
1707   SET_DECL_VALUE_EXPR (decl, t);
1708   DECL_HAS_VALUE_EXPR_P (decl) = 1;
1709 
1710   t = build_alloca_call_expr (DECL_SIZE_UNIT (decl), DECL_ALIGN (decl),
1711 			      max_int_size_in_bytes (TREE_TYPE (decl)));
1712   /* The call has been built for a variable-sized object.  */
1713   CALL_ALLOCA_FOR_VAR_P (t) = 1;
1714   t = fold_convert (ptr_type, t);
1715   t = build2 (MODIFY_EXPR, TREE_TYPE (addr), addr, t);
1716 
1717   gimplify_and_add (t, seq_p);
1718 
1719   /* Record the dynamic allocation associated with DECL if requested.  */
1720   if (flag_callgraph_info & CALLGRAPH_INFO_DYNAMIC_ALLOC)
1721     record_dynamic_alloc (decl);
1722 }
1723 
1724 /* A helper function to be called via walk_tree.  Mark all labels under *TP
1725    as being forced.  To be called for DECL_INITIAL of static variables.  */
1726 
1727 static tree
force_labels_r(tree * tp,int * walk_subtrees,void * data ATTRIBUTE_UNUSED)1728 force_labels_r (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
1729 {
1730   if (TYPE_P (*tp))
1731     *walk_subtrees = 0;
1732   if (TREE_CODE (*tp) == LABEL_DECL)
1733     {
1734       FORCED_LABEL (*tp) = 1;
1735       cfun->has_forced_label_in_static = 1;
1736     }
1737 
1738   return NULL_TREE;
1739 }
1740 
1741 /* Gimplify a DECL_EXPR node *STMT_P by making any necessary allocation
1742    and initialization explicit.  */
1743 
1744 static enum gimplify_status
gimplify_decl_expr(tree * stmt_p,gimple_seq * seq_p)1745 gimplify_decl_expr (tree *stmt_p, gimple_seq *seq_p)
1746 {
1747   tree stmt = *stmt_p;
1748   tree decl = DECL_EXPR_DECL (stmt);
1749 
1750   *stmt_p = NULL_TREE;
1751 
1752   if (TREE_TYPE (decl) == error_mark_node)
1753     return GS_ERROR;
1754 
1755   if ((TREE_CODE (decl) == TYPE_DECL
1756        || VAR_P (decl))
1757       && !TYPE_SIZES_GIMPLIFIED (TREE_TYPE (decl)))
1758     {
1759       gimplify_type_sizes (TREE_TYPE (decl), seq_p);
1760       if (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE)
1761 	gimplify_type_sizes (TREE_TYPE (TREE_TYPE (decl)), seq_p);
1762     }
1763 
1764   /* ??? DECL_ORIGINAL_TYPE is streamed for LTO so it needs to be gimplified
1765      in case its size expressions contain problematic nodes like CALL_EXPR.  */
1766   if (TREE_CODE (decl) == TYPE_DECL
1767       && DECL_ORIGINAL_TYPE (decl)
1768       && !TYPE_SIZES_GIMPLIFIED (DECL_ORIGINAL_TYPE (decl)))
1769     {
1770       gimplify_type_sizes (DECL_ORIGINAL_TYPE (decl), seq_p);
1771       if (TREE_CODE (DECL_ORIGINAL_TYPE (decl)) == REFERENCE_TYPE)
1772 	gimplify_type_sizes (TREE_TYPE (DECL_ORIGINAL_TYPE (decl)), seq_p);
1773     }
1774 
1775   if (VAR_P (decl) && !DECL_EXTERNAL (decl))
1776     {
1777       tree init = DECL_INITIAL (decl);
1778       bool is_vla = false;
1779 
1780       poly_uint64 size;
1781       if (!poly_int_tree_p (DECL_SIZE_UNIT (decl), &size)
1782 	  || (!TREE_STATIC (decl)
1783 	      && flag_stack_check == GENERIC_STACK_CHECK
1784 	      && maybe_gt (size,
1785 			   (unsigned HOST_WIDE_INT) STACK_CHECK_MAX_VAR_SIZE)))
1786 	{
1787 	  gimplify_vla_decl (decl, seq_p);
1788 	  is_vla = true;
1789 	}
1790 
1791       if (asan_poisoned_variables
1792 	  && !is_vla
1793 	  && TREE_ADDRESSABLE (decl)
1794 	  && !TREE_STATIC (decl)
1795 	  && !DECL_HAS_VALUE_EXPR_P (decl)
1796 	  && DECL_ALIGN (decl) <= MAX_SUPPORTED_STACK_ALIGNMENT
1797 	  && dbg_cnt (asan_use_after_scope)
1798 	  && !gimplify_omp_ctxp
1799 	  /* GNAT introduces temporaries to hold return values of calls in
1800 	     initializers of variables defined in other units, so the
1801 	     declaration of the variable is discarded completely.  We do not
1802 	     want to issue poison calls for such dropped variables.  */
1803 	  && (DECL_SEEN_IN_BIND_EXPR_P (decl)
1804 	      || (DECL_ARTIFICIAL (decl) && DECL_NAME (decl) == NULL_TREE)))
1805 	{
1806 	  asan_poisoned_variables->add (decl);
1807 	  asan_poison_variable (decl, false, seq_p);
1808 	  if (!DECL_ARTIFICIAL (decl) && gimplify_ctxp->live_switch_vars)
1809 	    gimplify_ctxp->live_switch_vars->add (decl);
1810 	}
1811 
1812       /* Some front ends do not explicitly declare all anonymous
1813 	 artificial variables.  We compensate here by declaring the
1814 	 variables, though it would be better if the front ends would
1815 	 explicitly declare them.  */
1816       if (!DECL_SEEN_IN_BIND_EXPR_P (decl)
1817 	  && DECL_ARTIFICIAL (decl) && DECL_NAME (decl) == NULL_TREE)
1818 	gimple_add_tmp_var (decl);
1819 
1820       if (init && init != error_mark_node)
1821 	{
1822 	  if (!TREE_STATIC (decl))
1823 	    {
1824 	      DECL_INITIAL (decl) = NULL_TREE;
1825 	      init = build2 (INIT_EXPR, void_type_node, decl, init);
1826 	      gimplify_and_add (init, seq_p);
1827 	      ggc_free (init);
1828 	    }
1829 	  else
1830 	    /* We must still examine initializers for static variables
1831 	       as they may contain a label address.  */
1832 	    walk_tree (&init, force_labels_r, NULL, NULL);
1833 	}
1834     }
1835 
1836   return GS_ALL_DONE;
1837 }
1838 
1839 /* Gimplify a LOOP_EXPR.  Normally this just involves gimplifying the body
1840    and replacing the LOOP_EXPR with goto, but if the loop contains an
1841    EXIT_EXPR, we need to append a label for it to jump to.  */
1842 
1843 static enum gimplify_status
gimplify_loop_expr(tree * expr_p,gimple_seq * pre_p)1844 gimplify_loop_expr (tree *expr_p, gimple_seq *pre_p)
1845 {
1846   tree saved_label = gimplify_ctxp->exit_label;
1847   tree start_label = create_artificial_label (UNKNOWN_LOCATION);
1848 
1849   gimplify_seq_add_stmt (pre_p, gimple_build_label (start_label));
1850 
1851   gimplify_ctxp->exit_label = NULL_TREE;
1852 
1853   gimplify_and_add (LOOP_EXPR_BODY (*expr_p), pre_p);
1854 
1855   gimplify_seq_add_stmt (pre_p, gimple_build_goto (start_label));
1856 
1857   if (gimplify_ctxp->exit_label)
1858     gimplify_seq_add_stmt (pre_p,
1859 			   gimple_build_label (gimplify_ctxp->exit_label));
1860 
1861   gimplify_ctxp->exit_label = saved_label;
1862 
1863   *expr_p = NULL;
1864   return GS_ALL_DONE;
1865 }
1866 
1867 /* Gimplify a statement list onto a sequence.  These may be created either
1868    by an enlightened front-end, or by shortcut_cond_expr.  */
1869 
1870 static enum gimplify_status
gimplify_statement_list(tree * expr_p,gimple_seq * pre_p)1871 gimplify_statement_list (tree *expr_p, gimple_seq *pre_p)
1872 {
1873   tree temp = voidify_wrapper_expr (*expr_p, NULL);
1874 
1875   tree_stmt_iterator i = tsi_start (*expr_p);
1876 
1877   while (!tsi_end_p (i))
1878     {
1879       gimplify_stmt (tsi_stmt_ptr (i), pre_p);
1880       tsi_delink (&i);
1881     }
1882 
1883   if (temp)
1884     {
1885       *expr_p = temp;
1886       return GS_OK;
1887     }
1888 
1889   return GS_ALL_DONE;
1890 }
1891 
1892 /* Callback for walk_gimple_seq.  */
1893 
1894 static tree
warn_switch_unreachable_r(gimple_stmt_iterator * gsi_p,bool * handled_ops_p,struct walk_stmt_info * wi)1895 warn_switch_unreachable_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
1896 			   struct walk_stmt_info *wi)
1897 {
1898   gimple *stmt = gsi_stmt (*gsi_p);
1899 
1900   *handled_ops_p = true;
1901   switch (gimple_code (stmt))
1902     {
1903     case GIMPLE_TRY:
1904       /* A compiler-generated cleanup or a user-written try block.
1905 	 If it's empty, don't dive into it--that would result in
1906 	 worse location info.  */
1907       if (gimple_try_eval (stmt) == NULL)
1908 	{
1909 	  wi->info = stmt;
1910 	  return integer_zero_node;
1911 	}
1912       /* Fall through.  */
1913     case GIMPLE_BIND:
1914     case GIMPLE_CATCH:
1915     case GIMPLE_EH_FILTER:
1916     case GIMPLE_TRANSACTION:
1917       /* Walk the sub-statements.  */
1918       *handled_ops_p = false;
1919       break;
1920 
1921     case GIMPLE_DEBUG:
1922       /* Ignore these.  We may generate them before declarations that
1923 	 are never executed.  If there's something to warn about,
1924 	 there will be non-debug stmts too, and we'll catch those.  */
1925       break;
1926 
1927     case GIMPLE_CALL:
1928       if (gimple_call_internal_p (stmt, IFN_ASAN_MARK))
1929 	{
1930 	  *handled_ops_p = false;
1931 	  break;
1932 	}
1933       /* Fall through.  */
1934     default:
1935       /* Save the first "real" statement (not a decl/lexical scope/...).  */
1936       wi->info = stmt;
1937       return integer_zero_node;
1938     }
1939   return NULL_TREE;
1940 }
1941 
1942 /* Possibly warn about unreachable statements between switch's controlling
1943    expression and the first case.  SEQ is the body of a switch expression.  */
1944 
1945 static void
maybe_warn_switch_unreachable(gimple_seq seq)1946 maybe_warn_switch_unreachable (gimple_seq seq)
1947 {
1948   if (!warn_switch_unreachable
1949       /* This warning doesn't play well with Fortran when optimizations
1950 	 are on.  */
1951       || lang_GNU_Fortran ()
1952       || seq == NULL)
1953     return;
1954 
1955   struct walk_stmt_info wi;
1956   memset (&wi, 0, sizeof (wi));
1957   walk_gimple_seq (seq, warn_switch_unreachable_r, NULL, &wi);
1958   gimple *stmt = (gimple *) wi.info;
1959 
1960   if (stmt && gimple_code (stmt) != GIMPLE_LABEL)
1961     {
1962       if (gimple_code (stmt) == GIMPLE_GOTO
1963 	  && TREE_CODE (gimple_goto_dest (stmt)) == LABEL_DECL
1964 	  && DECL_ARTIFICIAL (gimple_goto_dest (stmt)))
1965 	/* Don't warn for compiler-generated gotos.  These occur
1966 	   in Duff's devices, for example.  */;
1967       else
1968 	warning_at (gimple_location (stmt), OPT_Wswitch_unreachable,
1969 		    "statement will never be executed");
1970     }
1971 }
1972 
1973 
1974 /* A label entry that pairs label and a location.  */
1975 struct label_entry
1976 {
1977   tree label;
1978   location_t loc;
1979 };
1980 
1981 /* Find LABEL in vector of label entries VEC.  */
1982 
1983 static struct label_entry *
find_label_entry(const auto_vec<struct label_entry> * vec,tree label)1984 find_label_entry (const auto_vec<struct label_entry> *vec, tree label)
1985 {
1986   unsigned int i;
1987   struct label_entry *l;
1988 
1989   FOR_EACH_VEC_ELT (*vec, i, l)
1990     if (l->label == label)
1991       return l;
1992   return NULL;
1993 }
1994 
1995 /* Return true if LABEL, a LABEL_DECL, represents a case label
1996    in a vector of labels CASES.  */
1997 
1998 static bool
case_label_p(const vec<tree> * cases,tree label)1999 case_label_p (const vec<tree> *cases, tree label)
2000 {
2001   unsigned int i;
2002   tree l;
2003 
2004   FOR_EACH_VEC_ELT (*cases, i, l)
2005     if (CASE_LABEL (l) == label)
2006       return true;
2007   return false;
2008 }
2009 
2010 /* Find the last nondebug statement in a scope STMT.  */
2011 
2012 static gimple *
last_stmt_in_scope(gimple * stmt)2013 last_stmt_in_scope (gimple *stmt)
2014 {
2015   if (!stmt)
2016     return NULL;
2017 
2018   switch (gimple_code (stmt))
2019     {
2020     case GIMPLE_BIND:
2021       {
2022 	gbind *bind = as_a <gbind *> (stmt);
2023 	stmt = gimple_seq_last_nondebug_stmt (gimple_bind_body (bind));
2024 	return last_stmt_in_scope (stmt);
2025       }
2026 
2027     case GIMPLE_TRY:
2028       {
2029 	gtry *try_stmt = as_a <gtry *> (stmt);
2030 	stmt = gimple_seq_last_nondebug_stmt (gimple_try_eval (try_stmt));
2031 	gimple *last_eval = last_stmt_in_scope (stmt);
2032 	if (gimple_stmt_may_fallthru (last_eval)
2033 	    && (last_eval == NULL
2034 		|| !gimple_call_internal_p (last_eval, IFN_FALLTHROUGH))
2035 	    && gimple_try_kind (try_stmt) == GIMPLE_TRY_FINALLY)
2036 	  {
2037 	    stmt = gimple_seq_last_nondebug_stmt (gimple_try_cleanup (try_stmt));
2038 	    return last_stmt_in_scope (stmt);
2039 	  }
2040 	else
2041 	  return last_eval;
2042       }
2043 
2044     case GIMPLE_DEBUG:
2045       gcc_unreachable ();
2046 
2047     default:
2048       return stmt;
2049     }
2050 }
2051 
2052 /* Collect interesting labels in LABELS and return the statement preceding
2053    another case label, or a user-defined label.  Store a location useful
2054    to give warnings at *PREVLOC (usually the location of the returned
2055    statement or of its surrounding scope).  */
2056 
2057 static gimple *
collect_fallthrough_labels(gimple_stmt_iterator * gsi_p,auto_vec<struct label_entry> * labels,location_t * prevloc)2058 collect_fallthrough_labels (gimple_stmt_iterator *gsi_p,
2059 			    auto_vec <struct label_entry> *labels,
2060 			    location_t *prevloc)
2061 {
2062   gimple *prev = NULL;
2063 
2064   *prevloc = UNKNOWN_LOCATION;
2065   do
2066     {
2067       if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_BIND)
2068 	{
2069 	  /* Recognize the special GIMPLE_BIND added by gimplify_switch_expr,
2070 	     which starts on a GIMPLE_SWITCH and ends with a break label.
2071 	     Handle that as a single statement that can fall through.  */
2072 	  gbind *bind = as_a <gbind *> (gsi_stmt (*gsi_p));
2073 	  gimple *first = gimple_seq_first_stmt (gimple_bind_body (bind));
2074 	  gimple *last = gimple_seq_last_stmt (gimple_bind_body (bind));
2075 	  if (last
2076 	      && gimple_code (first) == GIMPLE_SWITCH
2077 	      && gimple_code (last) == GIMPLE_LABEL)
2078 	    {
2079 	      tree label = gimple_label_label (as_a <glabel *> (last));
2080 	      if (SWITCH_BREAK_LABEL_P (label))
2081 		{
2082 		  prev = bind;
2083 		  gsi_next (gsi_p);
2084 		  continue;
2085 		}
2086 	    }
2087 	}
2088       if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_BIND
2089 	  || gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_TRY)
2090 	{
2091 	  /* Nested scope.  Only look at the last statement of
2092 	     the innermost scope.  */
2093 	  location_t bind_loc = gimple_location (gsi_stmt (*gsi_p));
2094 	  gimple *last = last_stmt_in_scope (gsi_stmt (*gsi_p));
2095 	  if (last)
2096 	    {
2097 	      prev = last;
2098 	      /* It might be a label without a location.  Use the
2099 		 location of the scope then.  */
2100 	      if (!gimple_has_location (prev))
2101 		*prevloc = bind_loc;
2102 	    }
2103 	  gsi_next (gsi_p);
2104 	  continue;
2105 	}
2106 
2107       /* Ifs are tricky.  */
2108       if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_COND)
2109 	{
2110 	  gcond *cond_stmt = as_a <gcond *> (gsi_stmt (*gsi_p));
2111 	  tree false_lab = gimple_cond_false_label (cond_stmt);
2112 	  location_t if_loc = gimple_location (cond_stmt);
2113 
2114 	  /* If we have e.g.
2115 	       if (i > 1) goto <D.2259>; else goto D;
2116 	     we can't do much with the else-branch.  */
2117 	  if (!DECL_ARTIFICIAL (false_lab))
2118 	    break;
2119 
2120 	  /* Go on until the false label, then one step back.  */
2121 	  for (; !gsi_end_p (*gsi_p); gsi_next (gsi_p))
2122 	    {
2123 	      gimple *stmt = gsi_stmt (*gsi_p);
2124 	      if (gimple_code (stmt) == GIMPLE_LABEL
2125 		  && gimple_label_label (as_a <glabel *> (stmt)) == false_lab)
2126 		break;
2127 	    }
2128 
2129 	  /* Not found?  Oops.  */
2130 	  if (gsi_end_p (*gsi_p))
2131 	    break;
2132 
2133 	  struct label_entry l = { false_lab, if_loc };
2134 	  labels->safe_push (l);
2135 
2136 	  /* Go to the last statement of the then branch.  */
2137 	  gsi_prev (gsi_p);
2138 
2139 	  /* if (i != 0) goto <D.1759>; else goto <D.1760>;
2140 	     <D.1759>:
2141 	     <stmt>;
2142 	     goto <D.1761>;
2143 	     <D.1760>:
2144 	   */
2145 	  if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_GOTO
2146 	      && !gimple_has_location (gsi_stmt (*gsi_p)))
2147 	    {
2148 	      /* Look at the statement before, it might be
2149 		 attribute fallthrough, in which case don't warn.  */
2150 	      gsi_prev (gsi_p);
2151 	      bool fallthru_before_dest
2152 		= gimple_call_internal_p (gsi_stmt (*gsi_p), IFN_FALLTHROUGH);
2153 	      gsi_next (gsi_p);
2154 	      tree goto_dest = gimple_goto_dest (gsi_stmt (*gsi_p));
2155 	      if (!fallthru_before_dest)
2156 		{
2157 		  struct label_entry l = { goto_dest, if_loc };
2158 		  labels->safe_push (l);
2159 		}
2160 	    }
2161 	  /* And move back.  */
2162 	  gsi_next (gsi_p);
2163 	}
2164 
2165       /* Remember the last statement.  Skip labels that are of no interest
2166 	 to us.  */
2167       if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_LABEL)
2168 	{
2169 	  tree label = gimple_label_label (as_a <glabel *> (gsi_stmt (*gsi_p)));
2170 	  if (find_label_entry (labels, label))
2171 	    prev = gsi_stmt (*gsi_p);
2172 	}
2173       else if (gimple_call_internal_p (gsi_stmt (*gsi_p), IFN_ASAN_MARK))
2174 	;
2175       else if (gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_PREDICT)
2176 	;
2177       else if (!is_gimple_debug (gsi_stmt (*gsi_p)))
2178 	prev = gsi_stmt (*gsi_p);
2179       gsi_next (gsi_p);
2180     }
2181   while (!gsi_end_p (*gsi_p)
2182 	 /* Stop if we find a case or a user-defined label.  */
2183 	 && (gimple_code (gsi_stmt (*gsi_p)) != GIMPLE_LABEL
2184 	     || !gimple_has_location (gsi_stmt (*gsi_p))));
2185 
2186   if (prev && gimple_has_location (prev))
2187     *prevloc = gimple_location (prev);
2188   return prev;
2189 }
2190 
2191 /* Return true if the switch fallthough warning should occur.  LABEL is
2192    the label statement that we're falling through to.  */
2193 
2194 static bool
should_warn_for_implicit_fallthrough(gimple_stmt_iterator * gsi_p,tree label)2195 should_warn_for_implicit_fallthrough (gimple_stmt_iterator *gsi_p, tree label)
2196 {
2197   gimple_stmt_iterator gsi = *gsi_p;
2198 
2199   /* Don't warn if the label is marked with a "falls through" comment.  */
2200   if (FALLTHROUGH_LABEL_P (label))
2201     return false;
2202 
2203   /* Don't warn for non-case labels followed by a statement:
2204        case 0:
2205 	 foo ();
2206        label:
2207 	 bar ();
2208      as these are likely intentional.  */
2209   if (!case_label_p (&gimplify_ctxp->case_labels, label))
2210     {
2211       tree l;
2212       while (!gsi_end_p (gsi)
2213 	     && gimple_code (gsi_stmt (gsi)) == GIMPLE_LABEL
2214 	     && (l = gimple_label_label (as_a <glabel *> (gsi_stmt (gsi))))
2215 	     && !case_label_p (&gimplify_ctxp->case_labels, l))
2216 	gsi_next_nondebug (&gsi);
2217       if (gsi_end_p (gsi) || gimple_code (gsi_stmt (gsi)) != GIMPLE_LABEL)
2218 	return false;
2219     }
2220 
2221   /* Don't warn for terminated branches, i.e. when the subsequent case labels
2222      immediately breaks.  */
2223   gsi = *gsi_p;
2224 
2225   /* Skip all immediately following labels.  */
2226   while (!gsi_end_p (gsi)
2227 	 && (gimple_code (gsi_stmt (gsi)) == GIMPLE_LABEL
2228 	     || gimple_code (gsi_stmt (gsi)) == GIMPLE_PREDICT))
2229     gsi_next_nondebug (&gsi);
2230 
2231   /* { ... something; default:; } */
2232   if (gsi_end_p (gsi)
2233       /* { ... something; default: break; } or
2234 	 { ... something; default: goto L; } */
2235       || gimple_code (gsi_stmt (gsi)) == GIMPLE_GOTO
2236       /* { ... something; default: return; } */
2237       || gimple_code (gsi_stmt (gsi)) == GIMPLE_RETURN)
2238     return false;
2239 
2240   return true;
2241 }
2242 
2243 /* Callback for walk_gimple_seq.  */
2244 
2245 static tree
warn_implicit_fallthrough_r(gimple_stmt_iterator * gsi_p,bool * handled_ops_p,struct walk_stmt_info *)2246 warn_implicit_fallthrough_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
2247 			     struct walk_stmt_info *)
2248 {
2249   gimple *stmt = gsi_stmt (*gsi_p);
2250 
2251   *handled_ops_p = true;
2252   switch (gimple_code (stmt))
2253     {
2254     case GIMPLE_TRY:
2255     case GIMPLE_BIND:
2256     case GIMPLE_CATCH:
2257     case GIMPLE_EH_FILTER:
2258     case GIMPLE_TRANSACTION:
2259       /* Walk the sub-statements.  */
2260       *handled_ops_p = false;
2261       break;
2262 
2263     /* Find a sequence of form:
2264 
2265        GIMPLE_LABEL
2266        [...]
2267        <may fallthru stmt>
2268        GIMPLE_LABEL
2269 
2270        and possibly warn.  */
2271     case GIMPLE_LABEL:
2272       {
2273 	/* Found a label.  Skip all immediately following labels.  */
2274 	while (!gsi_end_p (*gsi_p)
2275 	       && gimple_code (gsi_stmt (*gsi_p)) == GIMPLE_LABEL)
2276 	  gsi_next_nondebug (gsi_p);
2277 
2278 	/* There might be no more statements.  */
2279 	if (gsi_end_p (*gsi_p))
2280 	  return integer_zero_node;
2281 
2282 	/* Vector of labels that fall through.  */
2283 	auto_vec <struct label_entry> labels;
2284 	location_t prevloc;
2285 	gimple *prev = collect_fallthrough_labels (gsi_p, &labels, &prevloc);
2286 
2287 	/* There might be no more statements.  */
2288 	if (gsi_end_p (*gsi_p))
2289 	  return integer_zero_node;
2290 
2291 	gimple *next = gsi_stmt (*gsi_p);
2292 	tree label;
2293 	/* If what follows is a label, then we may have a fallthrough.  */
2294 	if (gimple_code (next) == GIMPLE_LABEL
2295 	    && gimple_has_location (next)
2296 	    && (label = gimple_label_label (as_a <glabel *> (next)))
2297 	    && prev != NULL)
2298 	  {
2299 	    struct label_entry *l;
2300 	    bool warned_p = false;
2301 	    auto_diagnostic_group d;
2302 	    if (!should_warn_for_implicit_fallthrough (gsi_p, label))
2303 	      /* Quiet.  */;
2304 	    else if (gimple_code (prev) == GIMPLE_LABEL
2305 		     && (label = gimple_label_label (as_a <glabel *> (prev)))
2306 		     && (l = find_label_entry (&labels, label)))
2307 	      warned_p = warning_at (l->loc, OPT_Wimplicit_fallthrough_,
2308 				     "this statement may fall through");
2309 	    else if (!gimple_call_internal_p (prev, IFN_FALLTHROUGH)
2310 		     /* Try to be clever and don't warn when the statement
2311 			can't actually fall through.  */
2312 		     && gimple_stmt_may_fallthru (prev)
2313 		     && prevloc != UNKNOWN_LOCATION)
2314 	      warned_p = warning_at (prevloc,
2315 				     OPT_Wimplicit_fallthrough_,
2316 				     "this statement may fall through");
2317 	    if (warned_p)
2318 	      inform (gimple_location (next), "here");
2319 
2320 	    /* Mark this label as processed so as to prevent multiple
2321 	       warnings in nested switches.  */
2322 	    FALLTHROUGH_LABEL_P (label) = true;
2323 
2324 	    /* So that next warn_implicit_fallthrough_r will start looking for
2325 	       a new sequence starting with this label.  */
2326 	    gsi_prev (gsi_p);
2327 	  }
2328       }
2329       break;
2330    default:
2331       break;
2332     }
2333   return NULL_TREE;
2334 }
2335 
2336 /* Warn when a switch case falls through.  */
2337 
2338 static void
maybe_warn_implicit_fallthrough(gimple_seq seq)2339 maybe_warn_implicit_fallthrough (gimple_seq seq)
2340 {
2341   if (!warn_implicit_fallthrough)
2342     return;
2343 
2344   /* This warning is meant for C/C++/ObjC/ObjC++ only.  */
2345   if (!(lang_GNU_C ()
2346 	|| lang_GNU_CXX ()
2347 	|| lang_GNU_OBJC ()))
2348     return;
2349 
2350   struct walk_stmt_info wi;
2351   memset (&wi, 0, sizeof (wi));
2352   walk_gimple_seq (seq, warn_implicit_fallthrough_r, NULL, &wi);
2353 }
2354 
2355 /* Callback for walk_gimple_seq.  */
2356 
2357 static tree
expand_FALLTHROUGH_r(gimple_stmt_iterator * gsi_p,bool * handled_ops_p,struct walk_stmt_info * wi)2358 expand_FALLTHROUGH_r (gimple_stmt_iterator *gsi_p, bool *handled_ops_p,
2359 		      struct walk_stmt_info *wi)
2360 {
2361   gimple *stmt = gsi_stmt (*gsi_p);
2362 
2363   *handled_ops_p = true;
2364   switch (gimple_code (stmt))
2365     {
2366     case GIMPLE_TRY:
2367     case GIMPLE_BIND:
2368     case GIMPLE_CATCH:
2369     case GIMPLE_EH_FILTER:
2370     case GIMPLE_TRANSACTION:
2371       /* Walk the sub-statements.  */
2372       *handled_ops_p = false;
2373       break;
2374     case GIMPLE_CALL:
2375       if (gimple_call_internal_p (stmt, IFN_FALLTHROUGH))
2376 	{
2377 	  gsi_remove (gsi_p, true);
2378 	  if (gsi_end_p (*gsi_p))
2379 	    {
2380 	      *static_cast<location_t *>(wi->info) = gimple_location (stmt);
2381 	      return integer_zero_node;
2382 	    }
2383 
2384 	  bool found = false;
2385 	  location_t loc = gimple_location (stmt);
2386 
2387 	  gimple_stmt_iterator gsi2 = *gsi_p;
2388 	  stmt = gsi_stmt (gsi2);
2389 	  if (gimple_code (stmt) == GIMPLE_GOTO && !gimple_has_location (stmt))
2390 	    {
2391 	      /* Go on until the artificial label.  */
2392 	      tree goto_dest = gimple_goto_dest (stmt);
2393 	      for (; !gsi_end_p (gsi2); gsi_next (&gsi2))
2394 		{
2395 		  if (gimple_code (gsi_stmt (gsi2)) == GIMPLE_LABEL
2396 		      && gimple_label_label (as_a <glabel *> (gsi_stmt (gsi2)))
2397 			   == goto_dest)
2398 		    break;
2399 		}
2400 
2401 	      /* Not found?  Stop.  */
2402 	      if (gsi_end_p (gsi2))
2403 		break;
2404 
2405 	      /* Look one past it.  */
2406 	      gsi_next (&gsi2);
2407 	    }
2408 
2409 	  /* We're looking for a case label or default label here.  */
2410 	  while (!gsi_end_p (gsi2))
2411 	    {
2412 	      stmt = gsi_stmt (gsi2);
2413 	      if (gimple_code (stmt) == GIMPLE_LABEL)
2414 		{
2415 		  tree label = gimple_label_label (as_a <glabel *> (stmt));
2416 		  if (gimple_has_location (stmt) && DECL_ARTIFICIAL (label))
2417 		    {
2418 		      found = true;
2419 		      break;
2420 		    }
2421 		}
2422 	      else if (gimple_call_internal_p (stmt, IFN_ASAN_MARK))
2423 		;
2424 	      else if (!is_gimple_debug (stmt))
2425 		/* Anything else is not expected.  */
2426 		break;
2427 	      gsi_next (&gsi2);
2428 	    }
2429 	  if (!found)
2430 	    pedwarn (loc, 0, "attribute %<fallthrough%> not preceding "
2431 		     "a case label or default label");
2432 	}
2433       break;
2434     default:
2435       break;
2436     }
2437   return NULL_TREE;
2438 }
2439 
2440 /* Expand all FALLTHROUGH () calls in SEQ.  */
2441 
2442 static void
expand_FALLTHROUGH(gimple_seq * seq_p)2443 expand_FALLTHROUGH (gimple_seq *seq_p)
2444 {
2445   struct walk_stmt_info wi;
2446   location_t loc;
2447   memset (&wi, 0, sizeof (wi));
2448   wi.info = (void *) &loc;
2449   walk_gimple_seq_mod (seq_p, expand_FALLTHROUGH_r, NULL, &wi);
2450   if (wi.callback_result == integer_zero_node)
2451     /* We've found [[fallthrough]]; at the end of a switch, which the C++
2452        standard says is ill-formed; see [dcl.attr.fallthrough].  */
2453     pedwarn (loc, 0, "attribute %<fallthrough%> not preceding "
2454 	     "a case label or default label");
2455 }
2456 
2457 
2458 /* Gimplify a SWITCH_EXPR, and collect the vector of labels it can
2459    branch to.  */
2460 
2461 static enum gimplify_status
gimplify_switch_expr(tree * expr_p,gimple_seq * pre_p)2462 gimplify_switch_expr (tree *expr_p, gimple_seq *pre_p)
2463 {
2464   tree switch_expr = *expr_p;
2465   gimple_seq switch_body_seq = NULL;
2466   enum gimplify_status ret;
2467   tree index_type = TREE_TYPE (switch_expr);
2468   if (index_type == NULL_TREE)
2469     index_type = TREE_TYPE (SWITCH_COND (switch_expr));
2470 
2471   ret = gimplify_expr (&SWITCH_COND (switch_expr), pre_p, NULL, is_gimple_val,
2472                        fb_rvalue);
2473   if (ret == GS_ERROR || ret == GS_UNHANDLED)
2474     return ret;
2475 
2476   if (SWITCH_BODY (switch_expr))
2477     {
2478       vec<tree> labels;
2479       vec<tree> saved_labels;
2480       hash_set<tree> *saved_live_switch_vars = NULL;
2481       tree default_case = NULL_TREE;
2482       gswitch *switch_stmt;
2483 
2484       /* Save old labels, get new ones from body, then restore the old
2485          labels.  Save all the things from the switch body to append after.  */
2486       saved_labels = gimplify_ctxp->case_labels;
2487       gimplify_ctxp->case_labels.create (8);
2488 
2489       /* Do not create live_switch_vars if SWITCH_BODY is not a BIND_EXPR.  */
2490       saved_live_switch_vars = gimplify_ctxp->live_switch_vars;
2491       tree_code body_type = TREE_CODE (SWITCH_BODY (switch_expr));
2492       if (body_type == BIND_EXPR || body_type == STATEMENT_LIST)
2493 	gimplify_ctxp->live_switch_vars = new hash_set<tree> (4);
2494       else
2495 	gimplify_ctxp->live_switch_vars = NULL;
2496 
2497       bool old_in_switch_expr = gimplify_ctxp->in_switch_expr;
2498       gimplify_ctxp->in_switch_expr = true;
2499 
2500       gimplify_stmt (&SWITCH_BODY (switch_expr), &switch_body_seq);
2501 
2502       gimplify_ctxp->in_switch_expr = old_in_switch_expr;
2503       maybe_warn_switch_unreachable (switch_body_seq);
2504       maybe_warn_implicit_fallthrough (switch_body_seq);
2505       /* Only do this for the outermost GIMPLE_SWITCH.  */
2506       if (!gimplify_ctxp->in_switch_expr)
2507 	expand_FALLTHROUGH (&switch_body_seq);
2508 
2509       labels = gimplify_ctxp->case_labels;
2510       gimplify_ctxp->case_labels = saved_labels;
2511 
2512       if (gimplify_ctxp->live_switch_vars)
2513 	{
2514 	  gcc_assert (gimplify_ctxp->live_switch_vars->is_empty ());
2515 	  delete gimplify_ctxp->live_switch_vars;
2516 	}
2517       gimplify_ctxp->live_switch_vars = saved_live_switch_vars;
2518 
2519       preprocess_case_label_vec_for_gimple (labels, index_type,
2520 					    &default_case);
2521 
2522       bool add_bind = false;
2523       if (!default_case)
2524 	{
2525 	  glabel *new_default;
2526 
2527 	  default_case
2528 	    = build_case_label (NULL_TREE, NULL_TREE,
2529 				create_artificial_label (UNKNOWN_LOCATION));
2530 	  if (old_in_switch_expr)
2531 	    {
2532 	      SWITCH_BREAK_LABEL_P (CASE_LABEL (default_case)) = 1;
2533 	      add_bind = true;
2534 	    }
2535 	  new_default = gimple_build_label (CASE_LABEL (default_case));
2536 	  gimplify_seq_add_stmt (&switch_body_seq, new_default);
2537 	}
2538       else if (old_in_switch_expr)
2539 	{
2540 	  gimple *last = gimple_seq_last_stmt (switch_body_seq);
2541 	  if (last && gimple_code (last) == GIMPLE_LABEL)
2542 	    {
2543 	      tree label = gimple_label_label (as_a <glabel *> (last));
2544 	      if (SWITCH_BREAK_LABEL_P (label))
2545 		add_bind = true;
2546 	    }
2547 	}
2548 
2549       switch_stmt = gimple_build_switch (SWITCH_COND (switch_expr),
2550 					 default_case, labels);
2551       /* For the benefit of -Wimplicit-fallthrough, if switch_body_seq
2552 	 ends with a GIMPLE_LABEL holding SWITCH_BREAK_LABEL_P LABEL_DECL,
2553 	 wrap the GIMPLE_SWITCH up to that GIMPLE_LABEL into a GIMPLE_BIND,
2554 	 so that we can easily find the start and end of the switch
2555 	 statement.  */
2556       if (add_bind)
2557 	{
2558 	  gimple_seq bind_body = NULL;
2559 	  gimplify_seq_add_stmt (&bind_body, switch_stmt);
2560 	  gimple_seq_add_seq (&bind_body, switch_body_seq);
2561 	  gbind *bind = gimple_build_bind (NULL_TREE, bind_body, NULL_TREE);
2562 	  gimple_set_location (bind, EXPR_LOCATION (switch_expr));
2563 	  gimplify_seq_add_stmt (pre_p, bind);
2564 	}
2565       else
2566 	{
2567 	  gimplify_seq_add_stmt (pre_p, switch_stmt);
2568 	  gimplify_seq_add_seq (pre_p, switch_body_seq);
2569 	}
2570       labels.release ();
2571     }
2572   else
2573     gcc_unreachable ();
2574 
2575   return GS_ALL_DONE;
2576 }
2577 
2578 /* Gimplify the LABEL_EXPR pointed to by EXPR_P.  */
2579 
2580 static enum gimplify_status
gimplify_label_expr(tree * expr_p,gimple_seq * pre_p)2581 gimplify_label_expr (tree *expr_p, gimple_seq *pre_p)
2582 {
2583   gcc_assert (decl_function_context (LABEL_EXPR_LABEL (*expr_p))
2584 	      == current_function_decl);
2585 
2586   tree label = LABEL_EXPR_LABEL (*expr_p);
2587   glabel *label_stmt = gimple_build_label (label);
2588   gimple_set_location (label_stmt, EXPR_LOCATION (*expr_p));
2589   gimplify_seq_add_stmt (pre_p, label_stmt);
2590 
2591   if (lookup_attribute ("cold", DECL_ATTRIBUTES (label)))
2592     gimple_seq_add_stmt (pre_p, gimple_build_predict (PRED_COLD_LABEL,
2593 						      NOT_TAKEN));
2594   else if (lookup_attribute ("hot", DECL_ATTRIBUTES (label)))
2595     gimple_seq_add_stmt (pre_p, gimple_build_predict (PRED_HOT_LABEL,
2596 						      TAKEN));
2597 
2598   return GS_ALL_DONE;
2599 }
2600 
2601 /* Gimplify the CASE_LABEL_EXPR pointed to by EXPR_P.  */
2602 
2603 static enum gimplify_status
gimplify_case_label_expr(tree * expr_p,gimple_seq * pre_p)2604 gimplify_case_label_expr (tree *expr_p, gimple_seq *pre_p)
2605 {
2606   struct gimplify_ctx *ctxp;
2607   glabel *label_stmt;
2608 
2609   /* Invalid programs can play Duff's Device type games with, for example,
2610      #pragma omp parallel.  At least in the C front end, we don't
2611      detect such invalid branches until after gimplification, in the
2612      diagnose_omp_blocks pass.  */
2613   for (ctxp = gimplify_ctxp; ; ctxp = ctxp->prev_context)
2614     if (ctxp->case_labels.exists ())
2615       break;
2616 
2617   tree label = CASE_LABEL (*expr_p);
2618   label_stmt = gimple_build_label (label);
2619   gimple_set_location (label_stmt, EXPR_LOCATION (*expr_p));
2620   ctxp->case_labels.safe_push (*expr_p);
2621   gimplify_seq_add_stmt (pre_p, label_stmt);
2622 
2623   if (lookup_attribute ("cold", DECL_ATTRIBUTES (label)))
2624     gimple_seq_add_stmt (pre_p, gimple_build_predict (PRED_COLD_LABEL,
2625 						      NOT_TAKEN));
2626   else if (lookup_attribute ("hot", DECL_ATTRIBUTES (label)))
2627     gimple_seq_add_stmt (pre_p, gimple_build_predict (PRED_HOT_LABEL,
2628 						      TAKEN));
2629 
2630   return GS_ALL_DONE;
2631 }
2632 
2633 /* Build a GOTO to the LABEL_DECL pointed to by LABEL_P, building it first
2634    if necessary.  */
2635 
2636 tree
build_and_jump(tree * label_p)2637 build_and_jump (tree *label_p)
2638 {
2639   if (label_p == NULL)
2640     /* If there's nowhere to jump, just fall through.  */
2641     return NULL_TREE;
2642 
2643   if (*label_p == NULL_TREE)
2644     {
2645       tree label = create_artificial_label (UNKNOWN_LOCATION);
2646       *label_p = label;
2647     }
2648 
2649   return build1 (GOTO_EXPR, void_type_node, *label_p);
2650 }
2651 
2652 /* Gimplify an EXIT_EXPR by converting to a GOTO_EXPR inside a COND_EXPR.
2653    This also involves building a label to jump to and communicating it to
2654    gimplify_loop_expr through gimplify_ctxp->exit_label.  */
2655 
2656 static enum gimplify_status
gimplify_exit_expr(tree * expr_p)2657 gimplify_exit_expr (tree *expr_p)
2658 {
2659   tree cond = TREE_OPERAND (*expr_p, 0);
2660   tree expr;
2661 
2662   expr = build_and_jump (&gimplify_ctxp->exit_label);
2663   expr = build3 (COND_EXPR, void_type_node, cond, expr, NULL_TREE);
2664   *expr_p = expr;
2665 
2666   return GS_OK;
2667 }
2668 
2669 /* *EXPR_P is a COMPONENT_REF being used as an rvalue.  If its type is
2670    different from its canonical type, wrap the whole thing inside a
2671    NOP_EXPR and force the type of the COMPONENT_REF to be the canonical
2672    type.
2673 
2674    The canonical type of a COMPONENT_REF is the type of the field being
2675    referenced--unless the field is a bit-field which can be read directly
2676    in a smaller mode, in which case the canonical type is the
2677    sign-appropriate type corresponding to that mode.  */
2678 
2679 static void
canonicalize_component_ref(tree * expr_p)2680 canonicalize_component_ref (tree *expr_p)
2681 {
2682   tree expr = *expr_p;
2683   tree type;
2684 
2685   gcc_assert (TREE_CODE (expr) == COMPONENT_REF);
2686 
2687   if (INTEGRAL_TYPE_P (TREE_TYPE (expr)))
2688     type = TREE_TYPE (get_unwidened (expr, NULL_TREE));
2689   else
2690     type = TREE_TYPE (TREE_OPERAND (expr, 1));
2691 
2692   /* One could argue that all the stuff below is not necessary for
2693      the non-bitfield case and declare it a FE error if type
2694      adjustment would be needed.  */
2695   if (TREE_TYPE (expr) != type)
2696     {
2697 #ifdef ENABLE_TYPES_CHECKING
2698       tree old_type = TREE_TYPE (expr);
2699 #endif
2700       int type_quals;
2701 
2702       /* We need to preserve qualifiers and propagate them from
2703 	 operand 0.  */
2704       type_quals = TYPE_QUALS (type)
2705 	| TYPE_QUALS (TREE_TYPE (TREE_OPERAND (expr, 0)));
2706       if (TYPE_QUALS (type) != type_quals)
2707 	type = build_qualified_type (TYPE_MAIN_VARIANT (type), type_quals);
2708 
2709       /* Set the type of the COMPONENT_REF to the underlying type.  */
2710       TREE_TYPE (expr) = type;
2711 
2712 #ifdef ENABLE_TYPES_CHECKING
2713       /* It is now a FE error, if the conversion from the canonical
2714 	 type to the original expression type is not useless.  */
2715       gcc_assert (useless_type_conversion_p (old_type, type));
2716 #endif
2717     }
2718 }
2719 
2720 /* If a NOP conversion is changing a pointer to array of foo to a pointer
2721    to foo, embed that change in the ADDR_EXPR by converting
2722       T array[U];
2723       (T *)&array
2724    ==>
2725       &array[L]
2726    where L is the lower bound.  For simplicity, only do this for constant
2727    lower bound.
2728    The constraint is that the type of &array[L] is trivially convertible
2729    to T *.  */
2730 
2731 static void
canonicalize_addr_expr(tree * expr_p)2732 canonicalize_addr_expr (tree *expr_p)
2733 {
2734   tree expr = *expr_p;
2735   tree addr_expr = TREE_OPERAND (expr, 0);
2736   tree datype, ddatype, pddatype;
2737 
2738   /* We simplify only conversions from an ADDR_EXPR to a pointer type.  */
2739   if (!POINTER_TYPE_P (TREE_TYPE (expr))
2740       || TREE_CODE (addr_expr) != ADDR_EXPR)
2741     return;
2742 
2743   /* The addr_expr type should be a pointer to an array.  */
2744   datype = TREE_TYPE (TREE_TYPE (addr_expr));
2745   if (TREE_CODE (datype) != ARRAY_TYPE)
2746     return;
2747 
2748   /* The pointer to element type shall be trivially convertible to
2749      the expression pointer type.  */
2750   ddatype = TREE_TYPE (datype);
2751   pddatype = build_pointer_type (ddatype);
2752   if (!useless_type_conversion_p (TYPE_MAIN_VARIANT (TREE_TYPE (expr)),
2753 				  pddatype))
2754     return;
2755 
2756   /* The lower bound and element sizes must be constant.  */
2757   if (!TYPE_SIZE_UNIT (ddatype)
2758       || TREE_CODE (TYPE_SIZE_UNIT (ddatype)) != INTEGER_CST
2759       || !TYPE_DOMAIN (datype) || !TYPE_MIN_VALUE (TYPE_DOMAIN (datype))
2760       || TREE_CODE (TYPE_MIN_VALUE (TYPE_DOMAIN (datype))) != INTEGER_CST)
2761     return;
2762 
2763   /* All checks succeeded.  Build a new node to merge the cast.  */
2764   *expr_p = build4 (ARRAY_REF, ddatype, TREE_OPERAND (addr_expr, 0),
2765 		    TYPE_MIN_VALUE (TYPE_DOMAIN (datype)),
2766 		    NULL_TREE, NULL_TREE);
2767   *expr_p = build1 (ADDR_EXPR, pddatype, *expr_p);
2768 
2769   /* We can have stripped a required restrict qualifier above.  */
2770   if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
2771     *expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
2772 }
2773 
2774 /* *EXPR_P is a NOP_EXPR or CONVERT_EXPR.  Remove it and/or other conversions
2775    underneath as appropriate.  */
2776 
2777 static enum gimplify_status
gimplify_conversion(tree * expr_p)2778 gimplify_conversion (tree *expr_p)
2779 {
2780   location_t loc = EXPR_LOCATION (*expr_p);
2781   gcc_assert (CONVERT_EXPR_P (*expr_p));
2782 
2783   /* Then strip away all but the outermost conversion.  */
2784   STRIP_SIGN_NOPS (TREE_OPERAND (*expr_p, 0));
2785 
2786   /* And remove the outermost conversion if it's useless.  */
2787   if (tree_ssa_useless_type_conversion (*expr_p))
2788     *expr_p = TREE_OPERAND (*expr_p, 0);
2789 
2790   /* If we still have a conversion at the toplevel,
2791      then canonicalize some constructs.  */
2792   if (CONVERT_EXPR_P (*expr_p))
2793     {
2794       tree sub = TREE_OPERAND (*expr_p, 0);
2795 
2796       /* If a NOP conversion is changing the type of a COMPONENT_REF
2797 	 expression, then canonicalize its type now in order to expose more
2798 	 redundant conversions.  */
2799       if (TREE_CODE (sub) == COMPONENT_REF)
2800 	canonicalize_component_ref (&TREE_OPERAND (*expr_p, 0));
2801 
2802       /* If a NOP conversion is changing a pointer to array of foo
2803 	 to a pointer to foo, embed that change in the ADDR_EXPR.  */
2804       else if (TREE_CODE (sub) == ADDR_EXPR)
2805 	canonicalize_addr_expr (expr_p);
2806     }
2807 
2808   /* If we have a conversion to a non-register type force the
2809      use of a VIEW_CONVERT_EXPR instead.  */
2810   if (CONVERT_EXPR_P (*expr_p) && !is_gimple_reg_type (TREE_TYPE (*expr_p)))
2811     *expr_p = fold_build1_loc (loc, VIEW_CONVERT_EXPR, TREE_TYPE (*expr_p),
2812 			       TREE_OPERAND (*expr_p, 0));
2813 
2814   /* Canonicalize CONVERT_EXPR to NOP_EXPR.  */
2815   if (TREE_CODE (*expr_p) == CONVERT_EXPR)
2816     TREE_SET_CODE (*expr_p, NOP_EXPR);
2817 
2818   return GS_OK;
2819 }
2820 
2821 /* Gimplify a VAR_DECL or PARM_DECL.  Return GS_OK if we expanded a
2822    DECL_VALUE_EXPR, and it's worth re-examining things.  */
2823 
2824 static enum gimplify_status
gimplify_var_or_parm_decl(tree * expr_p)2825 gimplify_var_or_parm_decl (tree *expr_p)
2826 {
2827   tree decl = *expr_p;
2828 
2829   /* ??? If this is a local variable, and it has not been seen in any
2830      outer BIND_EXPR, then it's probably the result of a duplicate
2831      declaration, for which we've already issued an error.  It would
2832      be really nice if the front end wouldn't leak these at all.
2833      Currently the only known culprit is C++ destructors, as seen
2834      in g++.old-deja/g++.jason/binding.C.  */
2835   if (VAR_P (decl)
2836       && !DECL_SEEN_IN_BIND_EXPR_P (decl)
2837       && !TREE_STATIC (decl) && !DECL_EXTERNAL (decl)
2838       && decl_function_context (decl) == current_function_decl)
2839     {
2840       gcc_assert (seen_error ());
2841       return GS_ERROR;
2842     }
2843 
2844   /* When within an OMP context, notice uses of variables.  */
2845   if (gimplify_omp_ctxp && omp_notice_variable (gimplify_omp_ctxp, decl, true))
2846     return GS_ALL_DONE;
2847 
2848   /* If the decl is an alias for another expression, substitute it now.  */
2849   if (DECL_HAS_VALUE_EXPR_P (decl))
2850     {
2851       *expr_p = unshare_expr (DECL_VALUE_EXPR (decl));
2852       return GS_OK;
2853     }
2854 
2855   return GS_ALL_DONE;
2856 }
2857 
2858 /* Recalculate the value of the TREE_SIDE_EFFECTS flag for T.  */
2859 
2860 static void
recalculate_side_effects(tree t)2861 recalculate_side_effects (tree t)
2862 {
2863   enum tree_code code = TREE_CODE (t);
2864   int len = TREE_OPERAND_LENGTH (t);
2865   int i;
2866 
2867   switch (TREE_CODE_CLASS (code))
2868     {
2869     case tcc_expression:
2870       switch (code)
2871 	{
2872 	case INIT_EXPR:
2873 	case MODIFY_EXPR:
2874 	case VA_ARG_EXPR:
2875 	case PREDECREMENT_EXPR:
2876 	case PREINCREMENT_EXPR:
2877 	case POSTDECREMENT_EXPR:
2878 	case POSTINCREMENT_EXPR:
2879 	  /* All of these have side-effects, no matter what their
2880 	     operands are.  */
2881 	  return;
2882 
2883 	default:
2884 	  break;
2885 	}
2886       /* Fall through.  */
2887 
2888     case tcc_comparison:  /* a comparison expression */
2889     case tcc_unary:       /* a unary arithmetic expression */
2890     case tcc_binary:      /* a binary arithmetic expression */
2891     case tcc_reference:   /* a reference */
2892     case tcc_vl_exp:        /* a function call */
2893       TREE_SIDE_EFFECTS (t) = TREE_THIS_VOLATILE (t);
2894       for (i = 0; i < len; ++i)
2895 	{
2896 	  tree op = TREE_OPERAND (t, i);
2897 	  if (op && TREE_SIDE_EFFECTS (op))
2898 	    TREE_SIDE_EFFECTS (t) = 1;
2899 	}
2900       break;
2901 
2902     case tcc_constant:
2903       /* No side-effects.  */
2904       return;
2905 
2906     default:
2907       gcc_unreachable ();
2908    }
2909 }
2910 
2911 /* Gimplify the COMPONENT_REF, ARRAY_REF, REALPART_EXPR or IMAGPART_EXPR
2912    node *EXPR_P.
2913 
2914       compound_lval
2915 	      : min_lval '[' val ']'
2916 	      | min_lval '.' ID
2917 	      | compound_lval '[' val ']'
2918 	      | compound_lval '.' ID
2919 
2920    This is not part of the original SIMPLE definition, which separates
2921    array and member references, but it seems reasonable to handle them
2922    together.  Also, this way we don't run into problems with union
2923    aliasing; gcc requires that for accesses through a union to alias, the
2924    union reference must be explicit, which was not always the case when we
2925    were splitting up array and member refs.
2926 
2927    PRE_P points to the sequence where side effects that must happen before
2928      *EXPR_P should be stored.
2929 
2930    POST_P points to the sequence where side effects that must happen after
2931      *EXPR_P should be stored.  */
2932 
2933 static enum gimplify_status
gimplify_compound_lval(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,fallback_t fallback)2934 gimplify_compound_lval (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
2935 			fallback_t fallback)
2936 {
2937   tree *p;
2938   enum gimplify_status ret = GS_ALL_DONE, tret;
2939   int i;
2940   location_t loc = EXPR_LOCATION (*expr_p);
2941   tree expr = *expr_p;
2942 
2943   /* Create a stack of the subexpressions so later we can walk them in
2944      order from inner to outer.  */
2945   auto_vec<tree, 10> expr_stack;
2946 
2947   /* We can handle anything that get_inner_reference can deal with.  */
2948   for (p = expr_p; ; p = &TREE_OPERAND (*p, 0))
2949     {
2950     restart:
2951       /* Fold INDIRECT_REFs now to turn them into ARRAY_REFs.  */
2952       if (TREE_CODE (*p) == INDIRECT_REF)
2953 	*p = fold_indirect_ref_loc (loc, *p);
2954 
2955       if (handled_component_p (*p))
2956 	;
2957       /* Expand DECL_VALUE_EXPR now.  In some cases that may expose
2958 	 additional COMPONENT_REFs.  */
2959       else if ((VAR_P (*p) || TREE_CODE (*p) == PARM_DECL)
2960 	       && gimplify_var_or_parm_decl (p) == GS_OK)
2961 	goto restart;
2962       else
2963 	break;
2964 
2965       expr_stack.safe_push (*p);
2966     }
2967 
2968   gcc_assert (expr_stack.length ());
2969 
2970   /* Now EXPR_STACK is a stack of pointers to all the refs we've
2971      walked through and P points to the innermost expression.
2972 
2973      Java requires that we elaborated nodes in source order.  That
2974      means we must gimplify the inner expression followed by each of
2975      the indices, in order.  But we can't gimplify the inner
2976      expression until we deal with any variable bounds, sizes, or
2977      positions in order to deal with PLACEHOLDER_EXPRs.
2978 
2979      So we do this in three steps.  First we deal with the annotations
2980      for any variables in the components, then we gimplify the base,
2981      then we gimplify any indices, from left to right.  */
2982   for (i = expr_stack.length () - 1; i >= 0; i--)
2983     {
2984       tree t = expr_stack[i];
2985 
2986       if (TREE_CODE (t) == ARRAY_REF || TREE_CODE (t) == ARRAY_RANGE_REF)
2987 	{
2988 	  /* Gimplify the low bound and element type size and put them into
2989 	     the ARRAY_REF.  If these values are set, they have already been
2990 	     gimplified.  */
2991 	  if (TREE_OPERAND (t, 2) == NULL_TREE)
2992 	    {
2993 	      tree low = unshare_expr (array_ref_low_bound (t));
2994 	      if (!is_gimple_min_invariant (low))
2995 		{
2996 		  TREE_OPERAND (t, 2) = low;
2997 		  tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p,
2998 					post_p, is_gimple_reg,
2999 					fb_rvalue);
3000 		  ret = MIN (ret, tret);
3001 		}
3002 	    }
3003 	  else
3004 	    {
3005 	      tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p, post_p,
3006 				    is_gimple_reg, fb_rvalue);
3007 	      ret = MIN (ret, tret);
3008 	    }
3009 
3010 	  if (TREE_OPERAND (t, 3) == NULL_TREE)
3011 	    {
3012 	      tree elmt_size = array_ref_element_size (t);
3013 	      if (!is_gimple_min_invariant (elmt_size))
3014 		{
3015 		  elmt_size = unshare_expr (elmt_size);
3016 		  tree elmt_type = TREE_TYPE (TREE_TYPE (TREE_OPERAND (t, 0)));
3017 		  tree factor = size_int (TYPE_ALIGN_UNIT (elmt_type));
3018 
3019 		  /* Divide the element size by the alignment of the element
3020 		     type (above).  */
3021 		  elmt_size = size_binop_loc (loc, EXACT_DIV_EXPR,
3022 					      elmt_size, factor);
3023 
3024 		  TREE_OPERAND (t, 3) = elmt_size;
3025 		  tret = gimplify_expr (&TREE_OPERAND (t, 3), pre_p,
3026 					post_p, is_gimple_reg,
3027 					fb_rvalue);
3028 		  ret = MIN (ret, tret);
3029 		}
3030 	    }
3031 	  else
3032 	    {
3033 	      tret = gimplify_expr (&TREE_OPERAND (t, 3), pre_p, post_p,
3034 				    is_gimple_reg, fb_rvalue);
3035 	      ret = MIN (ret, tret);
3036 	    }
3037 	}
3038       else if (TREE_CODE (t) == COMPONENT_REF)
3039 	{
3040 	  /* Set the field offset into T and gimplify it.  */
3041 	  if (TREE_OPERAND (t, 2) == NULL_TREE)
3042 	    {
3043 	      tree offset = component_ref_field_offset (t);
3044 	      if (!is_gimple_min_invariant (offset))
3045 		{
3046 		  offset = unshare_expr (offset);
3047 		  tree field = TREE_OPERAND (t, 1);
3048 		  tree factor
3049 		    = size_int (DECL_OFFSET_ALIGN (field) / BITS_PER_UNIT);
3050 
3051 		  /* Divide the offset by its alignment.  */
3052 		  offset = size_binop_loc (loc, EXACT_DIV_EXPR,
3053 					   offset, factor);
3054 
3055 		  TREE_OPERAND (t, 2) = offset;
3056 		  tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p,
3057 					post_p, is_gimple_reg,
3058 					fb_rvalue);
3059 		  ret = MIN (ret, tret);
3060 		}
3061 	    }
3062 	  else
3063 	    {
3064 	      tret = gimplify_expr (&TREE_OPERAND (t, 2), pre_p, post_p,
3065 				    is_gimple_reg, fb_rvalue);
3066 	      ret = MIN (ret, tret);
3067 	    }
3068 	}
3069     }
3070 
3071   /* Step 2 is to gimplify the base expression.  Make sure lvalue is set
3072      so as to match the min_lval predicate.  Failure to do so may result
3073      in the creation of large aggregate temporaries.  */
3074   tret = gimplify_expr (p, pre_p, post_p, is_gimple_min_lval,
3075 			fallback | fb_lvalue);
3076   ret = MIN (ret, tret);
3077 
3078   /* And finally, the indices and operands of ARRAY_REF.  During this
3079      loop we also remove any useless conversions.  */
3080   for (; expr_stack.length () > 0; )
3081     {
3082       tree t = expr_stack.pop ();
3083 
3084       if (TREE_CODE (t) == ARRAY_REF || TREE_CODE (t) == ARRAY_RANGE_REF)
3085 	{
3086 	  /* Gimplify the dimension.  */
3087 	  if (!is_gimple_min_invariant (TREE_OPERAND (t, 1)))
3088 	    {
3089 	      tret = gimplify_expr (&TREE_OPERAND (t, 1), pre_p, post_p,
3090 				    is_gimple_val, fb_rvalue);
3091 	      ret = MIN (ret, tret);
3092 	    }
3093 	}
3094 
3095       STRIP_USELESS_TYPE_CONVERSION (TREE_OPERAND (t, 0));
3096 
3097       /* The innermost expression P may have originally had
3098 	 TREE_SIDE_EFFECTS set which would have caused all the outer
3099 	 expressions in *EXPR_P leading to P to also have had
3100 	 TREE_SIDE_EFFECTS set.  */
3101       recalculate_side_effects (t);
3102     }
3103 
3104   /* If the outermost expression is a COMPONENT_REF, canonicalize its type.  */
3105   if ((fallback & fb_rvalue) && TREE_CODE (*expr_p) == COMPONENT_REF)
3106     {
3107       canonicalize_component_ref (expr_p);
3108     }
3109 
3110   expr_stack.release ();
3111 
3112   gcc_assert (*expr_p == expr || ret != GS_ALL_DONE);
3113 
3114   return ret;
3115 }
3116 
3117 /*  Gimplify the self modifying expression pointed to by EXPR_P
3118     (++, --, +=, -=).
3119 
3120     PRE_P points to the list where side effects that must happen before
3121 	*EXPR_P should be stored.
3122 
3123     POST_P points to the list where side effects that must happen after
3124 	*EXPR_P should be stored.
3125 
3126     WANT_VALUE is nonzero iff we want to use the value of this expression
3127 	in another expression.
3128 
3129     ARITH_TYPE is the type the computation should be performed in.  */
3130 
3131 enum gimplify_status
gimplify_self_mod_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,bool want_value,tree arith_type)3132 gimplify_self_mod_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
3133 			bool want_value, tree arith_type)
3134 {
3135   enum tree_code code;
3136   tree lhs, lvalue, rhs, t1;
3137   gimple_seq post = NULL, *orig_post_p = post_p;
3138   bool postfix;
3139   enum tree_code arith_code;
3140   enum gimplify_status ret;
3141   location_t loc = EXPR_LOCATION (*expr_p);
3142 
3143   code = TREE_CODE (*expr_p);
3144 
3145   gcc_assert (code == POSTINCREMENT_EXPR || code == POSTDECREMENT_EXPR
3146 	      || code == PREINCREMENT_EXPR || code == PREDECREMENT_EXPR);
3147 
3148   /* Prefix or postfix?  */
3149   if (code == POSTINCREMENT_EXPR || code == POSTDECREMENT_EXPR)
3150     /* Faster to treat as prefix if result is not used.  */
3151     postfix = want_value;
3152   else
3153     postfix = false;
3154 
3155   /* For postfix, make sure the inner expression's post side effects
3156      are executed after side effects from this expression.  */
3157   if (postfix)
3158     post_p = &post;
3159 
3160   /* Add or subtract?  */
3161   if (code == PREINCREMENT_EXPR || code == POSTINCREMENT_EXPR)
3162     arith_code = PLUS_EXPR;
3163   else
3164     arith_code = MINUS_EXPR;
3165 
3166   /* Gimplify the LHS into a GIMPLE lvalue.  */
3167   lvalue = TREE_OPERAND (*expr_p, 0);
3168   ret = gimplify_expr (&lvalue, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
3169   if (ret == GS_ERROR)
3170     return ret;
3171 
3172   /* Extract the operands to the arithmetic operation.  */
3173   lhs = lvalue;
3174   rhs = TREE_OPERAND (*expr_p, 1);
3175 
3176   /* For postfix operator, we evaluate the LHS to an rvalue and then use
3177      that as the result value and in the postqueue operation.  */
3178   if (postfix)
3179     {
3180       ret = gimplify_expr (&lhs, pre_p, post_p, is_gimple_val, fb_rvalue);
3181       if (ret == GS_ERROR)
3182 	return ret;
3183 
3184       lhs = get_initialized_tmp_var (lhs, pre_p);
3185     }
3186 
3187   /* For POINTERs increment, use POINTER_PLUS_EXPR.  */
3188   if (POINTER_TYPE_P (TREE_TYPE (lhs)))
3189     {
3190       rhs = convert_to_ptrofftype_loc (loc, rhs);
3191       if (arith_code == MINUS_EXPR)
3192 	rhs = fold_build1_loc (loc, NEGATE_EXPR, TREE_TYPE (rhs), rhs);
3193       t1 = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (*expr_p), lhs, rhs);
3194     }
3195   else
3196     t1 = fold_convert (TREE_TYPE (*expr_p),
3197 		       fold_build2 (arith_code, arith_type,
3198 				    fold_convert (arith_type, lhs),
3199 				    fold_convert (arith_type, rhs)));
3200 
3201   if (postfix)
3202     {
3203       gimplify_assign (lvalue, t1, pre_p);
3204       gimplify_seq_add_seq (orig_post_p, post);
3205       *expr_p = lhs;
3206       return GS_ALL_DONE;
3207     }
3208   else
3209     {
3210       *expr_p = build2 (MODIFY_EXPR, TREE_TYPE (lvalue), lvalue, t1);
3211       return GS_OK;
3212     }
3213 }
3214 
3215 /* If *EXPR_P has a variable sized type, wrap it in a WITH_SIZE_EXPR.  */
3216 
3217 static void
maybe_with_size_expr(tree * expr_p)3218 maybe_with_size_expr (tree *expr_p)
3219 {
3220   tree expr = *expr_p;
3221   tree type = TREE_TYPE (expr);
3222   tree size;
3223 
3224   /* If we've already wrapped this or the type is error_mark_node, we can't do
3225      anything.  */
3226   if (TREE_CODE (expr) == WITH_SIZE_EXPR
3227       || type == error_mark_node)
3228     return;
3229 
3230   /* If the size isn't known or is a constant, we have nothing to do.  */
3231   size = TYPE_SIZE_UNIT (type);
3232   if (!size || poly_int_tree_p (size))
3233     return;
3234 
3235   /* Otherwise, make a WITH_SIZE_EXPR.  */
3236   size = unshare_expr (size);
3237   size = SUBSTITUTE_PLACEHOLDER_IN_EXPR (size, expr);
3238   *expr_p = build2 (WITH_SIZE_EXPR, type, expr, size);
3239 }
3240 
3241 /* Helper for gimplify_call_expr.  Gimplify a single argument *ARG_P
3242    Store any side-effects in PRE_P.  CALL_LOCATION is the location of
3243    the CALL_EXPR.  If ALLOW_SSA is set the actual parameter may be
3244    gimplified to an SSA name.  */
3245 
3246 enum gimplify_status
gimplify_arg(tree * arg_p,gimple_seq * pre_p,location_t call_location,bool allow_ssa)3247 gimplify_arg (tree *arg_p, gimple_seq *pre_p, location_t call_location,
3248 	      bool allow_ssa)
3249 {
3250   bool (*test) (tree);
3251   fallback_t fb;
3252 
3253   /* In general, we allow lvalues for function arguments to avoid
3254      extra overhead of copying large aggregates out of even larger
3255      aggregates into temporaries only to copy the temporaries to
3256      the argument list.  Make optimizers happy by pulling out to
3257      temporaries those types that fit in registers.  */
3258   if (is_gimple_reg_type (TREE_TYPE (*arg_p)))
3259     test = is_gimple_val, fb = fb_rvalue;
3260   else
3261     {
3262       test = is_gimple_lvalue, fb = fb_either;
3263       /* Also strip a TARGET_EXPR that would force an extra copy.  */
3264       if (TREE_CODE (*arg_p) == TARGET_EXPR)
3265 	{
3266 	  tree init = TARGET_EXPR_INITIAL (*arg_p);
3267 	  if (init
3268 	      && !VOID_TYPE_P (TREE_TYPE (init)))
3269 	    *arg_p = init;
3270 	}
3271     }
3272 
3273   /* If this is a variable sized type, we must remember the size.  */
3274   maybe_with_size_expr (arg_p);
3275 
3276   /* FIXME diagnostics: This will mess up gcc.dg/Warray-bounds.c.  */
3277   /* Make sure arguments have the same location as the function call
3278      itself.  */
3279   protected_set_expr_location (*arg_p, call_location);
3280 
3281   /* There is a sequence point before a function call.  Side effects in
3282      the argument list must occur before the actual call. So, when
3283      gimplifying arguments, force gimplify_expr to use an internal
3284      post queue which is then appended to the end of PRE_P.  */
3285   return gimplify_expr (arg_p, pre_p, NULL, test, fb, allow_ssa);
3286 }
3287 
3288 /* Don't fold inside offloading or taskreg regions: it can break code by
3289    adding decl references that weren't in the source.  We'll do it during
3290    omplower pass instead.  */
3291 
3292 static bool
maybe_fold_stmt(gimple_stmt_iterator * gsi)3293 maybe_fold_stmt (gimple_stmt_iterator *gsi)
3294 {
3295   struct gimplify_omp_ctx *ctx;
3296   for (ctx = gimplify_omp_ctxp; ctx; ctx = ctx->outer_context)
3297     if ((ctx->region_type & (ORT_TARGET | ORT_PARALLEL | ORT_TASK)) != 0)
3298       return false;
3299     else if ((ctx->region_type & ORT_HOST_TEAMS) == ORT_HOST_TEAMS)
3300       return false;
3301   /* Delay folding of builtins until the IL is in consistent state
3302      so the diagnostic machinery can do a better job.  */
3303   if (gimple_call_builtin_p (gsi_stmt (*gsi)))
3304     return false;
3305   return fold_stmt (gsi);
3306 }
3307 
3308 /* Gimplify the CALL_EXPR node *EXPR_P into the GIMPLE sequence PRE_P.
3309    WANT_VALUE is true if the result of the call is desired.  */
3310 
3311 static enum gimplify_status
gimplify_call_expr(tree * expr_p,gimple_seq * pre_p,bool want_value)3312 gimplify_call_expr (tree *expr_p, gimple_seq *pre_p, bool want_value)
3313 {
3314   tree fndecl, parms, p, fnptrtype;
3315   enum gimplify_status ret;
3316   int i, nargs;
3317   gcall *call;
3318   bool builtin_va_start_p = false;
3319   location_t loc = EXPR_LOCATION (*expr_p);
3320 
3321   gcc_assert (TREE_CODE (*expr_p) == CALL_EXPR);
3322 
3323   /* For reliable diagnostics during inlining, it is necessary that
3324      every call_expr be annotated with file and line.  */
3325   if (! EXPR_HAS_LOCATION (*expr_p))
3326     SET_EXPR_LOCATION (*expr_p, input_location);
3327 
3328   /* Gimplify internal functions created in the FEs.  */
3329   if (CALL_EXPR_FN (*expr_p) == NULL_TREE)
3330     {
3331       if (want_value)
3332 	return GS_ALL_DONE;
3333 
3334       nargs = call_expr_nargs (*expr_p);
3335       enum internal_fn ifn = CALL_EXPR_IFN (*expr_p);
3336       auto_vec<tree> vargs (nargs);
3337 
3338       for (i = 0; i < nargs; i++)
3339 	{
3340 	  gimplify_arg (&CALL_EXPR_ARG (*expr_p, i), pre_p,
3341 			EXPR_LOCATION (*expr_p));
3342 	  vargs.quick_push (CALL_EXPR_ARG (*expr_p, i));
3343 	}
3344 
3345       gcall *call = gimple_build_call_internal_vec (ifn, vargs);
3346       gimple_call_set_nothrow (call, TREE_NOTHROW (*expr_p));
3347       gimplify_seq_add_stmt (pre_p, call);
3348       return GS_ALL_DONE;
3349     }
3350 
3351   /* This may be a call to a builtin function.
3352 
3353      Builtin function calls may be transformed into different
3354      (and more efficient) builtin function calls under certain
3355      circumstances.  Unfortunately, gimplification can muck things
3356      up enough that the builtin expanders are not aware that certain
3357      transformations are still valid.
3358 
3359      So we attempt transformation/gimplification of the call before
3360      we gimplify the CALL_EXPR.  At this time we do not manage to
3361      transform all calls in the same manner as the expanders do, but
3362      we do transform most of them.  */
3363   fndecl = get_callee_fndecl (*expr_p);
3364   if (fndecl && fndecl_built_in_p (fndecl, BUILT_IN_NORMAL))
3365     switch (DECL_FUNCTION_CODE (fndecl))
3366       {
3367       CASE_BUILT_IN_ALLOCA:
3368 	/* If the call has been built for a variable-sized object, then we
3369 	   want to restore the stack level when the enclosing BIND_EXPR is
3370 	   exited to reclaim the allocated space; otherwise, we precisely
3371 	   need to do the opposite and preserve the latest stack level.  */
3372 	if (CALL_ALLOCA_FOR_VAR_P (*expr_p))
3373 	  gimplify_ctxp->save_stack = true;
3374 	else
3375 	  gimplify_ctxp->keep_stack = true;
3376 	break;
3377 
3378       case BUILT_IN_VA_START:
3379         {
3380 	  builtin_va_start_p = TRUE;
3381 	  if (call_expr_nargs (*expr_p) < 2)
3382 	    {
3383 	      error ("too few arguments to function %<va_start%>");
3384 	      *expr_p = build_empty_stmt (EXPR_LOCATION (*expr_p));
3385 	      return GS_OK;
3386 	    }
3387 
3388 	  if (fold_builtin_next_arg (*expr_p, true))
3389 	    {
3390 	      *expr_p = build_empty_stmt (EXPR_LOCATION (*expr_p));
3391 	      return GS_OK;
3392 	    }
3393 	  break;
3394 	}
3395 
3396       case BUILT_IN_EH_RETURN:
3397 	cfun->calls_eh_return = true;
3398 	break;
3399 
3400       case BUILT_IN_CLEAR_PADDING:
3401 	if (call_expr_nargs (*expr_p) == 1)
3402 	  {
3403 	    /* Remember the original type of the argument in an internal
3404 	       dummy second argument, as in GIMPLE pointer conversions are
3405 	       useless.  */
3406 	    p = CALL_EXPR_ARG (*expr_p, 0);
3407 	    *expr_p
3408 	      = build_call_expr_loc (EXPR_LOCATION (*expr_p), fndecl, 2, p,
3409 				     build_zero_cst (TREE_TYPE (p)));
3410 	    return GS_OK;
3411 	  }
3412 	break;
3413 
3414       default:
3415         ;
3416       }
3417   if (fndecl && fndecl_built_in_p (fndecl))
3418     {
3419       tree new_tree = fold_call_expr (input_location, *expr_p, !want_value);
3420       if (new_tree && new_tree != *expr_p)
3421 	{
3422 	  /* There was a transformation of this call which computes the
3423 	     same value, but in a more efficient way.  Return and try
3424 	     again.  */
3425 	  *expr_p = new_tree;
3426 	  return GS_OK;
3427 	}
3428     }
3429 
3430   /* Remember the original function pointer type.  */
3431   fnptrtype = TREE_TYPE (CALL_EXPR_FN (*expr_p));
3432 
3433   if (flag_openmp
3434       && fndecl
3435       && cfun
3436       && (cfun->curr_properties & PROP_gimple_any) == 0)
3437     {
3438       tree variant = omp_resolve_declare_variant (fndecl);
3439       if (variant != fndecl)
3440 	CALL_EXPR_FN (*expr_p) = build1 (ADDR_EXPR, fnptrtype, variant);
3441     }
3442 
3443   /* There is a sequence point before the call, so any side effects in
3444      the calling expression must occur before the actual call.  Force
3445      gimplify_expr to use an internal post queue.  */
3446   ret = gimplify_expr (&CALL_EXPR_FN (*expr_p), pre_p, NULL,
3447 		       is_gimple_call_addr, fb_rvalue);
3448 
3449   nargs = call_expr_nargs (*expr_p);
3450 
3451   /* Get argument types for verification.  */
3452   fndecl = get_callee_fndecl (*expr_p);
3453   parms = NULL_TREE;
3454   if (fndecl)
3455     parms = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
3456   else
3457     parms = TYPE_ARG_TYPES (TREE_TYPE (fnptrtype));
3458 
3459   if (fndecl && DECL_ARGUMENTS (fndecl))
3460     p = DECL_ARGUMENTS (fndecl);
3461   else if (parms)
3462     p = parms;
3463   else
3464     p = NULL_TREE;
3465   for (i = 0; i < nargs && p; i++, p = TREE_CHAIN (p))
3466     ;
3467 
3468   /* If the last argument is __builtin_va_arg_pack () and it is not
3469      passed as a named argument, decrease the number of CALL_EXPR
3470      arguments and set instead the CALL_EXPR_VA_ARG_PACK flag.  */
3471   if (!p
3472       && i < nargs
3473       && TREE_CODE (CALL_EXPR_ARG (*expr_p, nargs - 1)) == CALL_EXPR)
3474     {
3475       tree last_arg = CALL_EXPR_ARG (*expr_p, nargs - 1);
3476       tree last_arg_fndecl = get_callee_fndecl (last_arg);
3477 
3478       if (last_arg_fndecl
3479 	  && fndecl_built_in_p (last_arg_fndecl, BUILT_IN_VA_ARG_PACK))
3480 	{
3481 	  tree call = *expr_p;
3482 
3483 	  --nargs;
3484 	  *expr_p = build_call_array_loc (loc, TREE_TYPE (call),
3485 					  CALL_EXPR_FN (call),
3486 					  nargs, CALL_EXPR_ARGP (call));
3487 
3488 	  /* Copy all CALL_EXPR flags, location and block, except
3489 	     CALL_EXPR_VA_ARG_PACK flag.  */
3490 	  CALL_EXPR_STATIC_CHAIN (*expr_p) = CALL_EXPR_STATIC_CHAIN (call);
3491 	  CALL_EXPR_TAILCALL (*expr_p) = CALL_EXPR_TAILCALL (call);
3492 	  CALL_EXPR_RETURN_SLOT_OPT (*expr_p)
3493 	    = CALL_EXPR_RETURN_SLOT_OPT (call);
3494 	  CALL_FROM_THUNK_P (*expr_p) = CALL_FROM_THUNK_P (call);
3495 	  SET_EXPR_LOCATION (*expr_p, EXPR_LOCATION (call));
3496 
3497 	  /* Set CALL_EXPR_VA_ARG_PACK.  */
3498 	  CALL_EXPR_VA_ARG_PACK (*expr_p) = 1;
3499 	}
3500     }
3501 
3502   /* If the call returns twice then after building the CFG the call
3503      argument computations will no longer dominate the call because
3504      we add an abnormal incoming edge to the call.  So do not use SSA
3505      vars there.  */
3506   bool returns_twice = call_expr_flags (*expr_p) & ECF_RETURNS_TWICE;
3507 
3508   /* Gimplify the function arguments.  */
3509   if (nargs > 0)
3510     {
3511       for (i = (PUSH_ARGS_REVERSED ? nargs - 1 : 0);
3512            PUSH_ARGS_REVERSED ? i >= 0 : i < nargs;
3513            PUSH_ARGS_REVERSED ? i-- : i++)
3514         {
3515           enum gimplify_status t;
3516 
3517           /* Avoid gimplifying the second argument to va_start, which needs to
3518              be the plain PARM_DECL.  */
3519           if ((i != 1) || !builtin_va_start_p)
3520             {
3521               t = gimplify_arg (&CALL_EXPR_ARG (*expr_p, i), pre_p,
3522 				EXPR_LOCATION (*expr_p), ! returns_twice);
3523 
3524               if (t == GS_ERROR)
3525                 ret = GS_ERROR;
3526             }
3527         }
3528     }
3529 
3530   /* Gimplify the static chain.  */
3531   if (CALL_EXPR_STATIC_CHAIN (*expr_p))
3532     {
3533       if (fndecl && !DECL_STATIC_CHAIN (fndecl))
3534 	CALL_EXPR_STATIC_CHAIN (*expr_p) = NULL;
3535       else
3536 	{
3537 	  enum gimplify_status t;
3538 	  t = gimplify_arg (&CALL_EXPR_STATIC_CHAIN (*expr_p), pre_p,
3539 			    EXPR_LOCATION (*expr_p), ! returns_twice);
3540 	  if (t == GS_ERROR)
3541 	    ret = GS_ERROR;
3542 	}
3543     }
3544 
3545   /* Verify the function result.  */
3546   if (want_value && fndecl
3547       && VOID_TYPE_P (TREE_TYPE (TREE_TYPE (fnptrtype))))
3548     {
3549       error_at (loc, "using result of function returning %<void%>");
3550       ret = GS_ERROR;
3551     }
3552 
3553   /* Try this again in case gimplification exposed something.  */
3554   if (ret != GS_ERROR)
3555     {
3556       tree new_tree = fold_call_expr (input_location, *expr_p, !want_value);
3557 
3558       if (new_tree && new_tree != *expr_p)
3559 	{
3560 	  /* There was a transformation of this call which computes the
3561 	     same value, but in a more efficient way.  Return and try
3562 	     again.  */
3563 	  *expr_p = new_tree;
3564 	  return GS_OK;
3565 	}
3566     }
3567   else
3568     {
3569       *expr_p = error_mark_node;
3570       return GS_ERROR;
3571     }
3572 
3573   /* If the function is "const" or "pure", then clear TREE_SIDE_EFFECTS on its
3574      decl.  This allows us to eliminate redundant or useless
3575      calls to "const" functions.  */
3576   if (TREE_CODE (*expr_p) == CALL_EXPR)
3577     {
3578       int flags = call_expr_flags (*expr_p);
3579       if (flags & (ECF_CONST | ECF_PURE)
3580 	  /* An infinite loop is considered a side effect.  */
3581 	  && !(flags & (ECF_LOOPING_CONST_OR_PURE)))
3582 	TREE_SIDE_EFFECTS (*expr_p) = 0;
3583     }
3584 
3585   /* If the value is not needed by the caller, emit a new GIMPLE_CALL
3586      and clear *EXPR_P.  Otherwise, leave *EXPR_P in its gimplified
3587      form and delegate the creation of a GIMPLE_CALL to
3588      gimplify_modify_expr.  This is always possible because when
3589      WANT_VALUE is true, the caller wants the result of this call into
3590      a temporary, which means that we will emit an INIT_EXPR in
3591      internal_get_tmp_var which will then be handled by
3592      gimplify_modify_expr.  */
3593   if (!want_value)
3594     {
3595       /* The CALL_EXPR in *EXPR_P is already in GIMPLE form, so all we
3596 	 have to do is replicate it as a GIMPLE_CALL tuple.  */
3597       gimple_stmt_iterator gsi;
3598       call = gimple_build_call_from_tree (*expr_p, fnptrtype);
3599       notice_special_calls (call);
3600       gimplify_seq_add_stmt (pre_p, call);
3601       gsi = gsi_last (*pre_p);
3602       maybe_fold_stmt (&gsi);
3603       *expr_p = NULL_TREE;
3604     }
3605   else
3606     /* Remember the original function type.  */
3607     CALL_EXPR_FN (*expr_p) = build1 (NOP_EXPR, fnptrtype,
3608 				     CALL_EXPR_FN (*expr_p));
3609 
3610   return ret;
3611 }
3612 
3613 /* Handle shortcut semantics in the predicate operand of a COND_EXPR by
3614    rewriting it into multiple COND_EXPRs, and possibly GOTO_EXPRs.
3615 
3616    TRUE_LABEL_P and FALSE_LABEL_P point to the labels to jump to if the
3617    condition is true or false, respectively.  If null, we should generate
3618    our own to skip over the evaluation of this specific expression.
3619 
3620    LOCUS is the source location of the COND_EXPR.
3621 
3622    This function is the tree equivalent of do_jump.
3623 
3624    shortcut_cond_r should only be called by shortcut_cond_expr.  */
3625 
3626 static tree
shortcut_cond_r(tree pred,tree * true_label_p,tree * false_label_p,location_t locus)3627 shortcut_cond_r (tree pred, tree *true_label_p, tree *false_label_p,
3628 		 location_t locus)
3629 {
3630   tree local_label = NULL_TREE;
3631   tree t, expr = NULL;
3632 
3633   /* OK, it's not a simple case; we need to pull apart the COND_EXPR to
3634      retain the shortcut semantics.  Just insert the gotos here;
3635      shortcut_cond_expr will append the real blocks later.  */
3636   if (TREE_CODE (pred) == TRUTH_ANDIF_EXPR)
3637     {
3638       location_t new_locus;
3639 
3640       /* Turn if (a && b) into
3641 
3642 	 if (a); else goto no;
3643 	 if (b) goto yes; else goto no;
3644 	 (no:) */
3645 
3646       if (false_label_p == NULL)
3647 	false_label_p = &local_label;
3648 
3649       /* Keep the original source location on the first 'if'.  */
3650       t = shortcut_cond_r (TREE_OPERAND (pred, 0), NULL, false_label_p, locus);
3651       append_to_statement_list (t, &expr);
3652 
3653       /* Set the source location of the && on the second 'if'.  */
3654       new_locus = rexpr_location (pred, locus);
3655       t = shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p, false_label_p,
3656 			   new_locus);
3657       append_to_statement_list (t, &expr);
3658     }
3659   else if (TREE_CODE (pred) == TRUTH_ORIF_EXPR)
3660     {
3661       location_t new_locus;
3662 
3663       /* Turn if (a || b) into
3664 
3665 	 if (a) goto yes;
3666 	 if (b) goto yes; else goto no;
3667 	 (yes:) */
3668 
3669       if (true_label_p == NULL)
3670 	true_label_p = &local_label;
3671 
3672       /* Keep the original source location on the first 'if'.  */
3673       t = shortcut_cond_r (TREE_OPERAND (pred, 0), true_label_p, NULL, locus);
3674       append_to_statement_list (t, &expr);
3675 
3676       /* Set the source location of the || on the second 'if'.  */
3677       new_locus = rexpr_location (pred, locus);
3678       t = shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p, false_label_p,
3679 			   new_locus);
3680       append_to_statement_list (t, &expr);
3681     }
3682   else if (TREE_CODE (pred) == COND_EXPR
3683 	   && !VOID_TYPE_P (TREE_TYPE (TREE_OPERAND (pred, 1)))
3684 	   && !VOID_TYPE_P (TREE_TYPE (TREE_OPERAND (pred, 2))))
3685     {
3686       location_t new_locus;
3687 
3688       /* As long as we're messing with gotos, turn if (a ? b : c) into
3689 	 if (a)
3690 	   if (b) goto yes; else goto no;
3691 	 else
3692 	   if (c) goto yes; else goto no;
3693 
3694 	 Don't do this if one of the arms has void type, which can happen
3695 	 in C++ when the arm is throw.  */
3696 
3697       /* Keep the original source location on the first 'if'.  Set the source
3698 	 location of the ? on the second 'if'.  */
3699       new_locus = rexpr_location (pred, locus);
3700       expr = build3 (COND_EXPR, void_type_node, TREE_OPERAND (pred, 0),
3701 		     shortcut_cond_r (TREE_OPERAND (pred, 1), true_label_p,
3702 				      false_label_p, locus),
3703 		     shortcut_cond_r (TREE_OPERAND (pred, 2), true_label_p,
3704 				      false_label_p, new_locus));
3705     }
3706   else
3707     {
3708       expr = build3 (COND_EXPR, void_type_node, pred,
3709 		     build_and_jump (true_label_p),
3710 		     build_and_jump (false_label_p));
3711       SET_EXPR_LOCATION (expr, locus);
3712     }
3713 
3714   if (local_label)
3715     {
3716       t = build1 (LABEL_EXPR, void_type_node, local_label);
3717       append_to_statement_list (t, &expr);
3718     }
3719 
3720   return expr;
3721 }
3722 
3723 /* If EXPR is a GOTO_EXPR, return it.  If it is a STATEMENT_LIST, skip
3724    any of its leading DEBUG_BEGIN_STMTS and recurse on the subsequent
3725    statement, if it is the last one.  Otherwise, return NULL.  */
3726 
3727 static tree
find_goto(tree expr)3728 find_goto (tree expr)
3729 {
3730   if (!expr)
3731     return NULL_TREE;
3732 
3733   if (TREE_CODE (expr) == GOTO_EXPR)
3734     return expr;
3735 
3736   if (TREE_CODE (expr) != STATEMENT_LIST)
3737     return NULL_TREE;
3738 
3739   tree_stmt_iterator i = tsi_start (expr);
3740 
3741   while (!tsi_end_p (i) && TREE_CODE (tsi_stmt (i)) == DEBUG_BEGIN_STMT)
3742     tsi_next (&i);
3743 
3744   if (!tsi_one_before_end_p (i))
3745     return NULL_TREE;
3746 
3747   return find_goto (tsi_stmt (i));
3748 }
3749 
3750 /* Same as find_goto, except that it returns NULL if the destination
3751    is not a LABEL_DECL.  */
3752 
3753 static inline tree
find_goto_label(tree expr)3754 find_goto_label (tree expr)
3755 {
3756   tree dest = find_goto (expr);
3757   if (dest && TREE_CODE (GOTO_DESTINATION (dest)) == LABEL_DECL)
3758     return dest;
3759   return NULL_TREE;
3760 }
3761 
3762 /* Given a conditional expression EXPR with short-circuit boolean
3763    predicates using TRUTH_ANDIF_EXPR or TRUTH_ORIF_EXPR, break the
3764    predicate apart into the equivalent sequence of conditionals.  */
3765 
3766 static tree
shortcut_cond_expr(tree expr)3767 shortcut_cond_expr (tree expr)
3768 {
3769   tree pred = TREE_OPERAND (expr, 0);
3770   tree then_ = TREE_OPERAND (expr, 1);
3771   tree else_ = TREE_OPERAND (expr, 2);
3772   tree true_label, false_label, end_label, t;
3773   tree *true_label_p;
3774   tree *false_label_p;
3775   bool emit_end, emit_false, jump_over_else;
3776   bool then_se = then_ && TREE_SIDE_EFFECTS (then_);
3777   bool else_se = else_ && TREE_SIDE_EFFECTS (else_);
3778 
3779   /* First do simple transformations.  */
3780   if (!else_se)
3781     {
3782       /* If there is no 'else', turn
3783 	   if (a && b) then c
3784 	 into
3785 	   if (a) if (b) then c.  */
3786       while (TREE_CODE (pred) == TRUTH_ANDIF_EXPR)
3787 	{
3788 	  /* Keep the original source location on the first 'if'.  */
3789 	  location_t locus = EXPR_LOC_OR_LOC (expr, input_location);
3790 	  TREE_OPERAND (expr, 0) = TREE_OPERAND (pred, 1);
3791 	  /* Set the source location of the && on the second 'if'.  */
3792 	  if (rexpr_has_location (pred))
3793 	    SET_EXPR_LOCATION (expr, rexpr_location (pred));
3794 	  then_ = shortcut_cond_expr (expr);
3795 	  then_se = then_ && TREE_SIDE_EFFECTS (then_);
3796 	  pred = TREE_OPERAND (pred, 0);
3797 	  expr = build3 (COND_EXPR, void_type_node, pred, then_, NULL_TREE);
3798 	  SET_EXPR_LOCATION (expr, locus);
3799 	}
3800     }
3801 
3802   if (!then_se)
3803     {
3804       /* If there is no 'then', turn
3805 	   if (a || b); else d
3806 	 into
3807 	   if (a); else if (b); else d.  */
3808       while (TREE_CODE (pred) == TRUTH_ORIF_EXPR)
3809 	{
3810 	  /* Keep the original source location on the first 'if'.  */
3811 	  location_t locus = EXPR_LOC_OR_LOC (expr, input_location);
3812 	  TREE_OPERAND (expr, 0) = TREE_OPERAND (pred, 1);
3813 	  /* Set the source location of the || on the second 'if'.  */
3814 	  if (rexpr_has_location (pred))
3815 	    SET_EXPR_LOCATION (expr, rexpr_location (pred));
3816 	  else_ = shortcut_cond_expr (expr);
3817 	  else_se = else_ && TREE_SIDE_EFFECTS (else_);
3818 	  pred = TREE_OPERAND (pred, 0);
3819 	  expr = build3 (COND_EXPR, void_type_node, pred, NULL_TREE, else_);
3820 	  SET_EXPR_LOCATION (expr, locus);
3821 	}
3822     }
3823 
3824   /* If we're done, great.  */
3825   if (TREE_CODE (pred) != TRUTH_ANDIF_EXPR
3826       && TREE_CODE (pred) != TRUTH_ORIF_EXPR)
3827     return expr;
3828 
3829   /* Otherwise we need to mess with gotos.  Change
3830        if (a) c; else d;
3831      to
3832        if (a); else goto no;
3833        c; goto end;
3834        no: d; end:
3835      and recursively gimplify the condition.  */
3836 
3837   true_label = false_label = end_label = NULL_TREE;
3838 
3839   /* If our arms just jump somewhere, hijack those labels so we don't
3840      generate jumps to jumps.  */
3841 
3842   if (tree then_goto = find_goto_label (then_))
3843     {
3844       true_label = GOTO_DESTINATION (then_goto);
3845       then_ = NULL;
3846       then_se = false;
3847     }
3848 
3849   if (tree else_goto = find_goto_label (else_))
3850     {
3851       false_label = GOTO_DESTINATION (else_goto);
3852       else_ = NULL;
3853       else_se = false;
3854     }
3855 
3856   /* If we aren't hijacking a label for the 'then' branch, it falls through.  */
3857   if (true_label)
3858     true_label_p = &true_label;
3859   else
3860     true_label_p = NULL;
3861 
3862   /* The 'else' branch also needs a label if it contains interesting code.  */
3863   if (false_label || else_se)
3864     false_label_p = &false_label;
3865   else
3866     false_label_p = NULL;
3867 
3868   /* If there was nothing else in our arms, just forward the label(s).  */
3869   if (!then_se && !else_se)
3870     return shortcut_cond_r (pred, true_label_p, false_label_p,
3871 			    EXPR_LOC_OR_LOC (expr, input_location));
3872 
3873   /* If our last subexpression already has a terminal label, reuse it.  */
3874   if (else_se)
3875     t = expr_last (else_);
3876   else if (then_se)
3877     t = expr_last (then_);
3878   else
3879     t = NULL;
3880   if (t && TREE_CODE (t) == LABEL_EXPR)
3881     end_label = LABEL_EXPR_LABEL (t);
3882 
3883   /* If we don't care about jumping to the 'else' branch, jump to the end
3884      if the condition is false.  */
3885   if (!false_label_p)
3886     false_label_p = &end_label;
3887 
3888   /* We only want to emit these labels if we aren't hijacking them.  */
3889   emit_end = (end_label == NULL_TREE);
3890   emit_false = (false_label == NULL_TREE);
3891 
3892   /* We only emit the jump over the else clause if we have to--if the
3893      then clause may fall through.  Otherwise we can wind up with a
3894      useless jump and a useless label at the end of gimplified code,
3895      which will cause us to think that this conditional as a whole
3896      falls through even if it doesn't.  If we then inline a function
3897      which ends with such a condition, that can cause us to issue an
3898      inappropriate warning about control reaching the end of a
3899      non-void function.  */
3900   jump_over_else = block_may_fallthru (then_);
3901 
3902   pred = shortcut_cond_r (pred, true_label_p, false_label_p,
3903 			  EXPR_LOC_OR_LOC (expr, input_location));
3904 
3905   expr = NULL;
3906   append_to_statement_list (pred, &expr);
3907 
3908   append_to_statement_list (then_, &expr);
3909   if (else_se)
3910     {
3911       if (jump_over_else)
3912 	{
3913 	  tree last = expr_last (expr);
3914 	  t = build_and_jump (&end_label);
3915 	  if (rexpr_has_location (last))
3916 	    SET_EXPR_LOCATION (t, rexpr_location (last));
3917 	  append_to_statement_list (t, &expr);
3918 	}
3919       if (emit_false)
3920 	{
3921 	  t = build1 (LABEL_EXPR, void_type_node, false_label);
3922 	  append_to_statement_list (t, &expr);
3923 	}
3924       append_to_statement_list (else_, &expr);
3925     }
3926   if (emit_end && end_label)
3927     {
3928       t = build1 (LABEL_EXPR, void_type_node, end_label);
3929       append_to_statement_list (t, &expr);
3930     }
3931 
3932   return expr;
3933 }
3934 
3935 /* EXPR is used in a boolean context; make sure it has BOOLEAN_TYPE.  */
3936 
3937 tree
gimple_boolify(tree expr)3938 gimple_boolify (tree expr)
3939 {
3940   tree type = TREE_TYPE (expr);
3941   location_t loc = EXPR_LOCATION (expr);
3942 
3943   if (TREE_CODE (expr) == NE_EXPR
3944       && TREE_CODE (TREE_OPERAND (expr, 0)) == CALL_EXPR
3945       && integer_zerop (TREE_OPERAND (expr, 1)))
3946     {
3947       tree call = TREE_OPERAND (expr, 0);
3948       tree fn = get_callee_fndecl (call);
3949 
3950       /* For __builtin_expect ((long) (x), y) recurse into x as well
3951 	 if x is truth_value_p.  */
3952       if (fn
3953 	  && fndecl_built_in_p (fn, BUILT_IN_EXPECT)
3954 	  && call_expr_nargs (call) == 2)
3955 	{
3956 	  tree arg = CALL_EXPR_ARG (call, 0);
3957 	  if (arg)
3958 	    {
3959 	      if (TREE_CODE (arg) == NOP_EXPR
3960 		  && TREE_TYPE (arg) == TREE_TYPE (call))
3961 		arg = TREE_OPERAND (arg, 0);
3962 	      if (truth_value_p (TREE_CODE (arg)))
3963 		{
3964 		  arg = gimple_boolify (arg);
3965 		  CALL_EXPR_ARG (call, 0)
3966 		    = fold_convert_loc (loc, TREE_TYPE (call), arg);
3967 		}
3968 	    }
3969 	}
3970     }
3971 
3972   switch (TREE_CODE (expr))
3973     {
3974     case TRUTH_AND_EXPR:
3975     case TRUTH_OR_EXPR:
3976     case TRUTH_XOR_EXPR:
3977     case TRUTH_ANDIF_EXPR:
3978     case TRUTH_ORIF_EXPR:
3979       /* Also boolify the arguments of truth exprs.  */
3980       TREE_OPERAND (expr, 1) = gimple_boolify (TREE_OPERAND (expr, 1));
3981       /* FALLTHRU */
3982 
3983     case TRUTH_NOT_EXPR:
3984       TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
3985 
3986       /* These expressions always produce boolean results.  */
3987       if (TREE_CODE (type) != BOOLEAN_TYPE)
3988 	TREE_TYPE (expr) = boolean_type_node;
3989       return expr;
3990 
3991     case ANNOTATE_EXPR:
3992       switch ((enum annot_expr_kind) TREE_INT_CST_LOW (TREE_OPERAND (expr, 1)))
3993 	{
3994 	case annot_expr_ivdep_kind:
3995 	case annot_expr_unroll_kind:
3996 	case annot_expr_no_vector_kind:
3997 	case annot_expr_vector_kind:
3998 	case annot_expr_parallel_kind:
3999 	  TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
4000 	  if (TREE_CODE (type) != BOOLEAN_TYPE)
4001 	    TREE_TYPE (expr) = boolean_type_node;
4002 	  return expr;
4003 	default:
4004 	  gcc_unreachable ();
4005 	}
4006 
4007     default:
4008       if (COMPARISON_CLASS_P (expr))
4009 	{
4010 	  /* There expressions always prduce boolean results.  */
4011 	  if (TREE_CODE (type) != BOOLEAN_TYPE)
4012 	    TREE_TYPE (expr) = boolean_type_node;
4013 	  return expr;
4014 	}
4015       /* Other expressions that get here must have boolean values, but
4016 	 might need to be converted to the appropriate mode.  */
4017       if (TREE_CODE (type) == BOOLEAN_TYPE)
4018 	return expr;
4019       return fold_convert_loc (loc, boolean_type_node, expr);
4020     }
4021 }
4022 
4023 /* Given a conditional expression *EXPR_P without side effects, gimplify
4024    its operands.  New statements are inserted to PRE_P.  */
4025 
4026 static enum gimplify_status
gimplify_pure_cond_expr(tree * expr_p,gimple_seq * pre_p)4027 gimplify_pure_cond_expr (tree *expr_p, gimple_seq *pre_p)
4028 {
4029   tree expr = *expr_p, cond;
4030   enum gimplify_status ret, tret;
4031   enum tree_code code;
4032 
4033   cond = gimple_boolify (COND_EXPR_COND (expr));
4034 
4035   /* We need to handle && and || specially, as their gimplification
4036      creates pure cond_expr, thus leading to an infinite cycle otherwise.  */
4037   code = TREE_CODE (cond);
4038   if (code == TRUTH_ANDIF_EXPR)
4039     TREE_SET_CODE (cond, TRUTH_AND_EXPR);
4040   else if (code == TRUTH_ORIF_EXPR)
4041     TREE_SET_CODE (cond, TRUTH_OR_EXPR);
4042   ret = gimplify_expr (&cond, pre_p, NULL, is_gimple_condexpr, fb_rvalue);
4043   COND_EXPR_COND (*expr_p) = cond;
4044 
4045   tret = gimplify_expr (&COND_EXPR_THEN (expr), pre_p, NULL,
4046 				   is_gimple_val, fb_rvalue);
4047   ret = MIN (ret, tret);
4048   tret = gimplify_expr (&COND_EXPR_ELSE (expr), pre_p, NULL,
4049 				   is_gimple_val, fb_rvalue);
4050 
4051   return MIN (ret, tret);
4052 }
4053 
4054 /* Return true if evaluating EXPR could trap.
4055    EXPR is GENERIC, while tree_could_trap_p can be called
4056    only on GIMPLE.  */
4057 
4058 bool
generic_expr_could_trap_p(tree expr)4059 generic_expr_could_trap_p (tree expr)
4060 {
4061   unsigned i, n;
4062 
4063   if (!expr || is_gimple_val (expr))
4064     return false;
4065 
4066   if (!EXPR_P (expr) || tree_could_trap_p (expr))
4067     return true;
4068 
4069   n = TREE_OPERAND_LENGTH (expr);
4070   for (i = 0; i < n; i++)
4071     if (generic_expr_could_trap_p (TREE_OPERAND (expr, i)))
4072       return true;
4073 
4074   return false;
4075 }
4076 
4077 /*  Convert the conditional expression pointed to by EXPR_P '(p) ? a : b;'
4078     into
4079 
4080     if (p)			if (p)
4081       t1 = a;			  a;
4082     else		or	else
4083       t1 = b;			  b;
4084     t1;
4085 
4086     The second form is used when *EXPR_P is of type void.
4087 
4088     PRE_P points to the list where side effects that must happen before
4089       *EXPR_P should be stored.  */
4090 
4091 static enum gimplify_status
gimplify_cond_expr(tree * expr_p,gimple_seq * pre_p,fallback_t fallback)4092 gimplify_cond_expr (tree *expr_p, gimple_seq *pre_p, fallback_t fallback)
4093 {
4094   tree expr = *expr_p;
4095   tree type = TREE_TYPE (expr);
4096   location_t loc = EXPR_LOCATION (expr);
4097   tree tmp, arm1, arm2;
4098   enum gimplify_status ret;
4099   tree label_true, label_false, label_cont;
4100   bool have_then_clause_p, have_else_clause_p;
4101   gcond *cond_stmt;
4102   enum tree_code pred_code;
4103   gimple_seq seq = NULL;
4104 
4105   /* If this COND_EXPR has a value, copy the values into a temporary within
4106      the arms.  */
4107   if (!VOID_TYPE_P (type))
4108     {
4109       tree then_ = TREE_OPERAND (expr, 1), else_ = TREE_OPERAND (expr, 2);
4110       tree result;
4111 
4112       /* If either an rvalue is ok or we do not require an lvalue, create the
4113 	 temporary.  But we cannot do that if the type is addressable.  */
4114       if (((fallback & fb_rvalue) || !(fallback & fb_lvalue))
4115 	  && !TREE_ADDRESSABLE (type))
4116 	{
4117 	  if (gimplify_ctxp->allow_rhs_cond_expr
4118 	      /* If either branch has side effects or could trap, it can't be
4119 		 evaluated unconditionally.  */
4120 	      && !TREE_SIDE_EFFECTS (then_)
4121 	      && !generic_expr_could_trap_p (then_)
4122 	      && !TREE_SIDE_EFFECTS (else_)
4123 	      && !generic_expr_could_trap_p (else_))
4124 	    return gimplify_pure_cond_expr (expr_p, pre_p);
4125 
4126 	  tmp = create_tmp_var (type, "iftmp");
4127 	  result = tmp;
4128 	}
4129 
4130       /* Otherwise, only create and copy references to the values.  */
4131       else
4132 	{
4133 	  type = build_pointer_type (type);
4134 
4135 	  if (!VOID_TYPE_P (TREE_TYPE (then_)))
4136 	    then_ = build_fold_addr_expr_loc (loc, then_);
4137 
4138 	  if (!VOID_TYPE_P (TREE_TYPE (else_)))
4139 	    else_ = build_fold_addr_expr_loc (loc, else_);
4140 
4141 	  expr
4142 	    = build3 (COND_EXPR, type, TREE_OPERAND (expr, 0), then_, else_);
4143 
4144 	  tmp = create_tmp_var (type, "iftmp");
4145 	  result = build_simple_mem_ref_loc (loc, tmp);
4146 	}
4147 
4148       /* Build the new then clause, `tmp = then_;'.  But don't build the
4149 	 assignment if the value is void; in C++ it can be if it's a throw.  */
4150       if (!VOID_TYPE_P (TREE_TYPE (then_)))
4151 	TREE_OPERAND (expr, 1) = build2 (INIT_EXPR, type, tmp, then_);
4152 
4153       /* Similarly, build the new else clause, `tmp = else_;'.  */
4154       if (!VOID_TYPE_P (TREE_TYPE (else_)))
4155 	TREE_OPERAND (expr, 2) = build2 (INIT_EXPR, type, tmp, else_);
4156 
4157       TREE_TYPE (expr) = void_type_node;
4158       recalculate_side_effects (expr);
4159 
4160       /* Move the COND_EXPR to the prequeue.  */
4161       gimplify_stmt (&expr, pre_p);
4162 
4163       *expr_p = result;
4164       return GS_ALL_DONE;
4165     }
4166 
4167   /* Remove any COMPOUND_EXPR so the following cases will be caught.  */
4168   STRIP_TYPE_NOPS (TREE_OPERAND (expr, 0));
4169   if (TREE_CODE (TREE_OPERAND (expr, 0)) == COMPOUND_EXPR)
4170     gimplify_compound_expr (&TREE_OPERAND (expr, 0), pre_p, true);
4171 
4172   /* Make sure the condition has BOOLEAN_TYPE.  */
4173   TREE_OPERAND (expr, 0) = gimple_boolify (TREE_OPERAND (expr, 0));
4174 
4175   /* Break apart && and || conditions.  */
4176   if (TREE_CODE (TREE_OPERAND (expr, 0)) == TRUTH_ANDIF_EXPR
4177       || TREE_CODE (TREE_OPERAND (expr, 0)) == TRUTH_ORIF_EXPR)
4178     {
4179       expr = shortcut_cond_expr (expr);
4180 
4181       if (expr != *expr_p)
4182 	{
4183 	  *expr_p = expr;
4184 
4185 	  /* We can't rely on gimplify_expr to re-gimplify the expanded
4186 	     form properly, as cleanups might cause the target labels to be
4187 	     wrapped in a TRY_FINALLY_EXPR.  To prevent that, we need to
4188 	     set up a conditional context.  */
4189 	  gimple_push_condition ();
4190 	  gimplify_stmt (expr_p, &seq);
4191 	  gimple_pop_condition (pre_p);
4192 	  gimple_seq_add_seq (pre_p, seq);
4193 
4194 	  return GS_ALL_DONE;
4195 	}
4196     }
4197 
4198   /* Now do the normal gimplification.  */
4199 
4200   /* Gimplify condition.  */
4201   ret = gimplify_expr (&TREE_OPERAND (expr, 0), pre_p, NULL,
4202 		       is_gimple_condexpr_for_cond, fb_rvalue);
4203   if (ret == GS_ERROR)
4204     return GS_ERROR;
4205   gcc_assert (TREE_OPERAND (expr, 0) != NULL_TREE);
4206 
4207   gimple_push_condition ();
4208 
4209   have_then_clause_p = have_else_clause_p = false;
4210   label_true = find_goto_label (TREE_OPERAND (expr, 1));
4211   if (label_true
4212       && DECL_CONTEXT (GOTO_DESTINATION (label_true)) == current_function_decl
4213       /* For -O0 avoid this optimization if the COND_EXPR and GOTO_EXPR
4214 	 have different locations, otherwise we end up with incorrect
4215 	 location information on the branches.  */
4216       && (optimize
4217 	  || !EXPR_HAS_LOCATION (expr)
4218 	  || !rexpr_has_location (label_true)
4219 	  || EXPR_LOCATION (expr) == rexpr_location (label_true)))
4220     {
4221       have_then_clause_p = true;
4222       label_true = GOTO_DESTINATION (label_true);
4223     }
4224   else
4225     label_true = create_artificial_label (UNKNOWN_LOCATION);
4226   label_false = find_goto_label (TREE_OPERAND (expr, 2));
4227   if (label_false
4228       && DECL_CONTEXT (GOTO_DESTINATION (label_false)) == current_function_decl
4229       /* For -O0 avoid this optimization if the COND_EXPR and GOTO_EXPR
4230 	 have different locations, otherwise we end up with incorrect
4231 	 location information on the branches.  */
4232       && (optimize
4233 	  || !EXPR_HAS_LOCATION (expr)
4234 	  || !rexpr_has_location (label_false)
4235 	  || EXPR_LOCATION (expr) == rexpr_location (label_false)))
4236     {
4237       have_else_clause_p = true;
4238       label_false = GOTO_DESTINATION (label_false);
4239     }
4240   else
4241     label_false = create_artificial_label (UNKNOWN_LOCATION);
4242 
4243   gimple_cond_get_ops_from_tree (COND_EXPR_COND (expr), &pred_code, &arm1,
4244 				 &arm2);
4245   cond_stmt = gimple_build_cond (pred_code, arm1, arm2, label_true,
4246 				 label_false);
4247   gimple_set_no_warning (cond_stmt, TREE_NO_WARNING (COND_EXPR_COND (expr)));
4248   gimplify_seq_add_stmt (&seq, cond_stmt);
4249   gimple_stmt_iterator gsi = gsi_last (seq);
4250   maybe_fold_stmt (&gsi);
4251 
4252   label_cont = NULL_TREE;
4253   if (!have_then_clause_p)
4254     {
4255       /* For if (...) {} else { code; } put label_true after
4256 	 the else block.  */
4257       if (TREE_OPERAND (expr, 1) == NULL_TREE
4258 	  && !have_else_clause_p
4259 	  && TREE_OPERAND (expr, 2) != NULL_TREE)
4260 	label_cont = label_true;
4261       else
4262 	{
4263 	  gimplify_seq_add_stmt (&seq, gimple_build_label (label_true));
4264 	  have_then_clause_p = gimplify_stmt (&TREE_OPERAND (expr, 1), &seq);
4265 	  /* For if (...) { code; } else {} or
4266 	     if (...) { code; } else goto label; or
4267 	     if (...) { code; return; } else { ... }
4268 	     label_cont isn't needed.  */
4269 	  if (!have_else_clause_p
4270 	      && TREE_OPERAND (expr, 2) != NULL_TREE
4271 	      && gimple_seq_may_fallthru (seq))
4272 	    {
4273 	      gimple *g;
4274 	      label_cont = create_artificial_label (UNKNOWN_LOCATION);
4275 
4276 	      g = gimple_build_goto (label_cont);
4277 
4278 	      /* GIMPLE_COND's are very low level; they have embedded
4279 		 gotos.  This particular embedded goto should not be marked
4280 		 with the location of the original COND_EXPR, as it would
4281 		 correspond to the COND_EXPR's condition, not the ELSE or the
4282 		 THEN arms.  To avoid marking it with the wrong location, flag
4283 		 it as "no location".  */
4284 	      gimple_set_do_not_emit_location (g);
4285 
4286 	      gimplify_seq_add_stmt (&seq, g);
4287 	    }
4288 	}
4289     }
4290   if (!have_else_clause_p)
4291     {
4292       gimplify_seq_add_stmt (&seq, gimple_build_label (label_false));
4293       have_else_clause_p = gimplify_stmt (&TREE_OPERAND (expr, 2), &seq);
4294     }
4295   if (label_cont)
4296     gimplify_seq_add_stmt (&seq, gimple_build_label (label_cont));
4297 
4298   gimple_pop_condition (pre_p);
4299   gimple_seq_add_seq (pre_p, seq);
4300 
4301   if (ret == GS_ERROR)
4302     ; /* Do nothing.  */
4303   else if (have_then_clause_p || have_else_clause_p)
4304     ret = GS_ALL_DONE;
4305   else
4306     {
4307       /* Both arms are empty; replace the COND_EXPR with its predicate.  */
4308       expr = TREE_OPERAND (expr, 0);
4309       gimplify_stmt (&expr, pre_p);
4310     }
4311 
4312   *expr_p = NULL;
4313   return ret;
4314 }
4315 
4316 /* Prepare the node pointed to by EXPR_P, an is_gimple_addressable expression,
4317    to be marked addressable.
4318 
4319    We cannot rely on such an expression being directly markable if a temporary
4320    has been created by the gimplification.  In this case, we create another
4321    temporary and initialize it with a copy, which will become a store after we
4322    mark it addressable.  This can happen if the front-end passed us something
4323    that it could not mark addressable yet, like a Fortran pass-by-reference
4324    parameter (int) floatvar.  */
4325 
4326 static void
prepare_gimple_addressable(tree * expr_p,gimple_seq * seq_p)4327 prepare_gimple_addressable (tree *expr_p, gimple_seq *seq_p)
4328 {
4329   while (handled_component_p (*expr_p))
4330     expr_p = &TREE_OPERAND (*expr_p, 0);
4331   if (is_gimple_reg (*expr_p))
4332     {
4333       /* Do not allow an SSA name as the temporary.  */
4334       tree var = get_initialized_tmp_var (*expr_p, seq_p, NULL, false);
4335       DECL_NOT_GIMPLE_REG_P (var) = 1;
4336       *expr_p = var;
4337     }
4338 }
4339 
4340 /* A subroutine of gimplify_modify_expr.  Replace a MODIFY_EXPR with
4341    a call to __builtin_memcpy.  */
4342 
4343 static enum gimplify_status
gimplify_modify_expr_to_memcpy(tree * expr_p,tree size,bool want_value,gimple_seq * seq_p)4344 gimplify_modify_expr_to_memcpy (tree *expr_p, tree size, bool want_value,
4345     				gimple_seq *seq_p)
4346 {
4347   tree t, to, to_ptr, from, from_ptr;
4348   gcall *gs;
4349   location_t loc = EXPR_LOCATION (*expr_p);
4350 
4351   to = TREE_OPERAND (*expr_p, 0);
4352   from = TREE_OPERAND (*expr_p, 1);
4353 
4354   /* Mark the RHS addressable.  Beware that it may not be possible to do so
4355      directly if a temporary has been created by the gimplification.  */
4356   prepare_gimple_addressable (&from, seq_p);
4357 
4358   mark_addressable (from);
4359   from_ptr = build_fold_addr_expr_loc (loc, from);
4360   gimplify_arg (&from_ptr, seq_p, loc);
4361 
4362   mark_addressable (to);
4363   to_ptr = build_fold_addr_expr_loc (loc, to);
4364   gimplify_arg (&to_ptr, seq_p, loc);
4365 
4366   t = builtin_decl_implicit (BUILT_IN_MEMCPY);
4367 
4368   gs = gimple_build_call (t, 3, to_ptr, from_ptr, size);
4369   gimple_call_set_alloca_for_var (gs, true);
4370 
4371   if (want_value)
4372     {
4373       /* tmp = memcpy() */
4374       t = create_tmp_var (TREE_TYPE (to_ptr));
4375       gimple_call_set_lhs (gs, t);
4376       gimplify_seq_add_stmt (seq_p, gs);
4377 
4378       *expr_p = build_simple_mem_ref (t);
4379       return GS_ALL_DONE;
4380     }
4381 
4382   gimplify_seq_add_stmt (seq_p, gs);
4383   *expr_p = NULL;
4384   return GS_ALL_DONE;
4385 }
4386 
4387 /* A subroutine of gimplify_modify_expr.  Replace a MODIFY_EXPR with
4388    a call to __builtin_memset.  In this case we know that the RHS is
4389    a CONSTRUCTOR with an empty element list.  */
4390 
4391 static enum gimplify_status
gimplify_modify_expr_to_memset(tree * expr_p,tree size,bool want_value,gimple_seq * seq_p)4392 gimplify_modify_expr_to_memset (tree *expr_p, tree size, bool want_value,
4393     				gimple_seq *seq_p)
4394 {
4395   tree t, from, to, to_ptr;
4396   gcall *gs;
4397   location_t loc = EXPR_LOCATION (*expr_p);
4398 
4399   /* Assert our assumptions, to abort instead of producing wrong code
4400      silently if they are not met.  Beware that the RHS CONSTRUCTOR might
4401      not be immediately exposed.  */
4402   from = TREE_OPERAND (*expr_p, 1);
4403   if (TREE_CODE (from) == WITH_SIZE_EXPR)
4404     from = TREE_OPERAND (from, 0);
4405 
4406   gcc_assert (TREE_CODE (from) == CONSTRUCTOR
4407 	      && vec_safe_is_empty (CONSTRUCTOR_ELTS (from)));
4408 
4409   /* Now proceed.  */
4410   to = TREE_OPERAND (*expr_p, 0);
4411 
4412   to_ptr = build_fold_addr_expr_loc (loc, to);
4413   gimplify_arg (&to_ptr, seq_p, loc);
4414   t = builtin_decl_implicit (BUILT_IN_MEMSET);
4415 
4416   gs = gimple_build_call (t, 3, to_ptr, integer_zero_node, size);
4417 
4418   if (want_value)
4419     {
4420       /* tmp = memset() */
4421       t = create_tmp_var (TREE_TYPE (to_ptr));
4422       gimple_call_set_lhs (gs, t);
4423       gimplify_seq_add_stmt (seq_p, gs);
4424 
4425       *expr_p = build1 (INDIRECT_REF, TREE_TYPE (to), t);
4426       return GS_ALL_DONE;
4427     }
4428 
4429   gimplify_seq_add_stmt (seq_p, gs);
4430   *expr_p = NULL;
4431   return GS_ALL_DONE;
4432 }
4433 
4434 /* A subroutine of gimplify_init_ctor_preeval.  Called via walk_tree,
4435    determine, cautiously, if a CONSTRUCTOR overlaps the lhs of an
4436    assignment.  Return non-null if we detect a potential overlap.  */
4437 
4438 struct gimplify_init_ctor_preeval_data
4439 {
4440   /* The base decl of the lhs object.  May be NULL, in which case we
4441      have to assume the lhs is indirect.  */
4442   tree lhs_base_decl;
4443 
4444   /* The alias set of the lhs object.  */
4445   alias_set_type lhs_alias_set;
4446 };
4447 
4448 static tree
gimplify_init_ctor_preeval_1(tree * tp,int * walk_subtrees,void * xdata)4449 gimplify_init_ctor_preeval_1 (tree *tp, int *walk_subtrees, void *xdata)
4450 {
4451   struct gimplify_init_ctor_preeval_data *data
4452     = (struct gimplify_init_ctor_preeval_data *) xdata;
4453   tree t = *tp;
4454 
4455   /* If we find the base object, obviously we have overlap.  */
4456   if (data->lhs_base_decl == t)
4457     return t;
4458 
4459   /* If the constructor component is indirect, determine if we have a
4460      potential overlap with the lhs.  The only bits of information we
4461      have to go on at this point are addressability and alias sets.  */
4462   if ((INDIRECT_REF_P (t)
4463        || TREE_CODE (t) == MEM_REF)
4464       && (!data->lhs_base_decl || TREE_ADDRESSABLE (data->lhs_base_decl))
4465       && alias_sets_conflict_p (data->lhs_alias_set, get_alias_set (t)))
4466     return t;
4467 
4468   /* If the constructor component is a call, determine if it can hide a
4469      potential overlap with the lhs through an INDIRECT_REF like above.
4470      ??? Ugh - this is completely broken.  In fact this whole analysis
4471      doesn't look conservative.  */
4472   if (TREE_CODE (t) == CALL_EXPR)
4473     {
4474       tree type, fntype = TREE_TYPE (TREE_TYPE (CALL_EXPR_FN (t)));
4475 
4476       for (type = TYPE_ARG_TYPES (fntype); type; type = TREE_CHAIN (type))
4477 	if (POINTER_TYPE_P (TREE_VALUE (type))
4478 	    && (!data->lhs_base_decl || TREE_ADDRESSABLE (data->lhs_base_decl))
4479 	    && alias_sets_conflict_p (data->lhs_alias_set,
4480 				      get_alias_set
4481 				        (TREE_TYPE (TREE_VALUE (type)))))
4482 	  return t;
4483     }
4484 
4485   if (IS_TYPE_OR_DECL_P (t))
4486     *walk_subtrees = 0;
4487   return NULL;
4488 }
4489 
4490 /* A subroutine of gimplify_init_constructor.  Pre-evaluate EXPR,
4491    force values that overlap with the lhs (as described by *DATA)
4492    into temporaries.  */
4493 
4494 static void
gimplify_init_ctor_preeval(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,struct gimplify_init_ctor_preeval_data * data)4495 gimplify_init_ctor_preeval (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
4496 			    struct gimplify_init_ctor_preeval_data *data)
4497 {
4498   enum gimplify_status one;
4499 
4500   /* If the value is constant, then there's nothing to pre-evaluate.  */
4501   if (TREE_CONSTANT (*expr_p))
4502     {
4503       /* Ensure it does not have side effects, it might contain a reference to
4504 	 the object we're initializing.  */
4505       gcc_assert (!TREE_SIDE_EFFECTS (*expr_p));
4506       return;
4507     }
4508 
4509   /* If the type has non-trivial constructors, we can't pre-evaluate.  */
4510   if (TREE_ADDRESSABLE (TREE_TYPE (*expr_p)))
4511     return;
4512 
4513   /* Recurse for nested constructors.  */
4514   if (TREE_CODE (*expr_p) == CONSTRUCTOR)
4515     {
4516       unsigned HOST_WIDE_INT ix;
4517       constructor_elt *ce;
4518       vec<constructor_elt, va_gc> *v = CONSTRUCTOR_ELTS (*expr_p);
4519 
4520       FOR_EACH_VEC_SAFE_ELT (v, ix, ce)
4521 	gimplify_init_ctor_preeval (&ce->value, pre_p, post_p, data);
4522 
4523       return;
4524     }
4525 
4526   /* If this is a variable sized type, we must remember the size.  */
4527   maybe_with_size_expr (expr_p);
4528 
4529   /* Gimplify the constructor element to something appropriate for the rhs
4530      of a MODIFY_EXPR.  Given that we know the LHS is an aggregate, we know
4531      the gimplifier will consider this a store to memory.  Doing this
4532      gimplification now means that we won't have to deal with complicated
4533      language-specific trees, nor trees like SAVE_EXPR that can induce
4534      exponential search behavior.  */
4535   one = gimplify_expr (expr_p, pre_p, post_p, is_gimple_mem_rhs, fb_rvalue);
4536   if (one == GS_ERROR)
4537     {
4538       *expr_p = NULL;
4539       return;
4540     }
4541 
4542   /* If we gimplified to a bare decl, we can be sure that it doesn't overlap
4543      with the lhs, since "a = { .x=a }" doesn't make sense.  This will
4544      always be true for all scalars, since is_gimple_mem_rhs insists on a
4545      temporary variable for them.  */
4546   if (DECL_P (*expr_p))
4547     return;
4548 
4549   /* If this is of variable size, we have no choice but to assume it doesn't
4550      overlap since we can't make a temporary for it.  */
4551   if (TREE_CODE (TYPE_SIZE (TREE_TYPE (*expr_p))) != INTEGER_CST)
4552     return;
4553 
4554   /* Otherwise, we must search for overlap ...  */
4555   if (!walk_tree (expr_p, gimplify_init_ctor_preeval_1, data, NULL))
4556     return;
4557 
4558   /* ... and if found, force the value into a temporary.  */
4559   *expr_p = get_formal_tmp_var (*expr_p, pre_p);
4560 }
4561 
4562 /* A subroutine of gimplify_init_ctor_eval.  Create a loop for
4563    a RANGE_EXPR in a CONSTRUCTOR for an array.
4564 
4565       var = lower;
4566     loop_entry:
4567       object[var] = value;
4568       if (var == upper)
4569 	goto loop_exit;
4570       var = var + 1;
4571       goto loop_entry;
4572     loop_exit:
4573 
4574    We increment var _after_ the loop exit check because we might otherwise
4575    fail if upper == TYPE_MAX_VALUE (type for upper).
4576 
4577    Note that we never have to deal with SAVE_EXPRs here, because this has
4578    already been taken care of for us, in gimplify_init_ctor_preeval().  */
4579 
4580 static void gimplify_init_ctor_eval (tree, vec<constructor_elt, va_gc> *,
4581 				     gimple_seq *, bool);
4582 
4583 static void
gimplify_init_ctor_eval_range(tree object,tree lower,tree upper,tree value,tree array_elt_type,gimple_seq * pre_p,bool cleared)4584 gimplify_init_ctor_eval_range (tree object, tree lower, tree upper,
4585 			       tree value, tree array_elt_type,
4586 			       gimple_seq *pre_p, bool cleared)
4587 {
4588   tree loop_entry_label, loop_exit_label, fall_thru_label;
4589   tree var, var_type, cref, tmp;
4590 
4591   loop_entry_label = create_artificial_label (UNKNOWN_LOCATION);
4592   loop_exit_label = create_artificial_label (UNKNOWN_LOCATION);
4593   fall_thru_label = create_artificial_label (UNKNOWN_LOCATION);
4594 
4595   /* Create and initialize the index variable.  */
4596   var_type = TREE_TYPE (upper);
4597   var = create_tmp_var (var_type);
4598   gimplify_seq_add_stmt (pre_p, gimple_build_assign (var, lower));
4599 
4600   /* Add the loop entry label.  */
4601   gimplify_seq_add_stmt (pre_p, gimple_build_label (loop_entry_label));
4602 
4603   /* Build the reference.  */
4604   cref = build4 (ARRAY_REF, array_elt_type, unshare_expr (object),
4605 		 var, NULL_TREE, NULL_TREE);
4606 
4607   /* If we are a constructor, just call gimplify_init_ctor_eval to do
4608      the store.  Otherwise just assign value to the reference.  */
4609 
4610   if (TREE_CODE (value) == CONSTRUCTOR)
4611     /* NB we might have to call ourself recursively through
4612        gimplify_init_ctor_eval if the value is a constructor.  */
4613     gimplify_init_ctor_eval (cref, CONSTRUCTOR_ELTS (value),
4614 			     pre_p, cleared);
4615   else
4616     {
4617       if (gimplify_expr (&value, pre_p, NULL, is_gimple_val, fb_rvalue)
4618 	  != GS_ERROR)
4619 	gimplify_seq_add_stmt (pre_p, gimple_build_assign (cref, value));
4620     }
4621 
4622   /* We exit the loop when the index var is equal to the upper bound.  */
4623   gimplify_seq_add_stmt (pre_p,
4624 			 gimple_build_cond (EQ_EXPR, var, upper,
4625 					    loop_exit_label, fall_thru_label));
4626 
4627   gimplify_seq_add_stmt (pre_p, gimple_build_label (fall_thru_label));
4628 
4629   /* Otherwise, increment the index var...  */
4630   tmp = build2 (PLUS_EXPR, var_type, var,
4631 		fold_convert (var_type, integer_one_node));
4632   gimplify_seq_add_stmt (pre_p, gimple_build_assign (var, tmp));
4633 
4634   /* ...and jump back to the loop entry.  */
4635   gimplify_seq_add_stmt (pre_p, gimple_build_goto (loop_entry_label));
4636 
4637   /* Add the loop exit label.  */
4638   gimplify_seq_add_stmt (pre_p, gimple_build_label (loop_exit_label));
4639 }
4640 
4641 /* Return true if FDECL is accessing a field that is zero sized.  */
4642 
4643 static bool
zero_sized_field_decl(const_tree fdecl)4644 zero_sized_field_decl (const_tree fdecl)
4645 {
4646   if (TREE_CODE (fdecl) == FIELD_DECL && DECL_SIZE (fdecl)
4647       && integer_zerop (DECL_SIZE (fdecl)))
4648     return true;
4649   return false;
4650 }
4651 
4652 /* Return true if TYPE is zero sized.  */
4653 
4654 static bool
zero_sized_type(const_tree type)4655 zero_sized_type (const_tree type)
4656 {
4657   if (AGGREGATE_TYPE_P (type) && TYPE_SIZE (type)
4658       && integer_zerop (TYPE_SIZE (type)))
4659     return true;
4660   return false;
4661 }
4662 
4663 /* A subroutine of gimplify_init_constructor.  Generate individual
4664    MODIFY_EXPRs for a CONSTRUCTOR.  OBJECT is the LHS against which the
4665    assignments should happen.  ELTS is the CONSTRUCTOR_ELTS of the
4666    CONSTRUCTOR.  CLEARED is true if the entire LHS object has been
4667    zeroed first.  */
4668 
4669 static void
gimplify_init_ctor_eval(tree object,vec<constructor_elt,va_gc> * elts,gimple_seq * pre_p,bool cleared)4670 gimplify_init_ctor_eval (tree object, vec<constructor_elt, va_gc> *elts,
4671 			 gimple_seq *pre_p, bool cleared)
4672 {
4673   tree array_elt_type = NULL;
4674   unsigned HOST_WIDE_INT ix;
4675   tree purpose, value;
4676 
4677   if (TREE_CODE (TREE_TYPE (object)) == ARRAY_TYPE)
4678     array_elt_type = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (object)));
4679 
4680   FOR_EACH_CONSTRUCTOR_ELT (elts, ix, purpose, value)
4681     {
4682       tree cref;
4683 
4684       /* NULL values are created above for gimplification errors.  */
4685       if (value == NULL)
4686 	continue;
4687 
4688       if (cleared && initializer_zerop (value))
4689 	continue;
4690 
4691       /* ??? Here's to hoping the front end fills in all of the indices,
4692 	 so we don't have to figure out what's missing ourselves.  */
4693       gcc_assert (purpose);
4694 
4695       /* Skip zero-sized fields, unless value has side-effects.  This can
4696 	 happen with calls to functions returning a zero-sized type, which
4697 	 we shouldn't discard.  As a number of downstream passes don't
4698 	 expect sets of zero-sized fields, we rely on the gimplification of
4699 	 the MODIFY_EXPR we make below to drop the assignment statement.  */
4700       if (! TREE_SIDE_EFFECTS (value) && zero_sized_field_decl (purpose))
4701 	continue;
4702 
4703       /* If we have a RANGE_EXPR, we have to build a loop to assign the
4704 	 whole range.  */
4705       if (TREE_CODE (purpose) == RANGE_EXPR)
4706 	{
4707 	  tree lower = TREE_OPERAND (purpose, 0);
4708 	  tree upper = TREE_OPERAND (purpose, 1);
4709 
4710 	  /* If the lower bound is equal to upper, just treat it as if
4711 	     upper was the index.  */
4712 	  if (simple_cst_equal (lower, upper))
4713 	    purpose = upper;
4714 	  else
4715 	    {
4716 	      gimplify_init_ctor_eval_range (object, lower, upper, value,
4717 					     array_elt_type, pre_p, cleared);
4718 	      continue;
4719 	    }
4720 	}
4721 
4722       if (array_elt_type)
4723 	{
4724 	  /* Do not use bitsizetype for ARRAY_REF indices.  */
4725 	  if (TYPE_DOMAIN (TREE_TYPE (object)))
4726 	    purpose
4727 	      = fold_convert (TREE_TYPE (TYPE_DOMAIN (TREE_TYPE (object))),
4728 			      purpose);
4729 	  cref = build4 (ARRAY_REF, array_elt_type, unshare_expr (object),
4730 			 purpose, NULL_TREE, NULL_TREE);
4731 	}
4732       else
4733 	{
4734 	  gcc_assert (TREE_CODE (purpose) == FIELD_DECL);
4735 	  cref = build3 (COMPONENT_REF, TREE_TYPE (purpose),
4736 			 unshare_expr (object), purpose, NULL_TREE);
4737 	}
4738 
4739       if (TREE_CODE (value) == CONSTRUCTOR
4740 	  && TREE_CODE (TREE_TYPE (value)) != VECTOR_TYPE)
4741 	gimplify_init_ctor_eval (cref, CONSTRUCTOR_ELTS (value),
4742 				 pre_p, cleared);
4743       else
4744 	{
4745 	  tree init = build2 (INIT_EXPR, TREE_TYPE (cref), cref, value);
4746 	  gimplify_and_add (init, pre_p);
4747 	  ggc_free (init);
4748 	}
4749     }
4750 }
4751 
4752 /* Return the appropriate RHS predicate for this LHS.  */
4753 
4754 gimple_predicate
rhs_predicate_for(tree lhs)4755 rhs_predicate_for (tree lhs)
4756 {
4757   if (is_gimple_reg (lhs))
4758     return is_gimple_reg_rhs_or_call;
4759   else
4760     return is_gimple_mem_rhs_or_call;
4761 }
4762 
4763 /* Return the initial guess for an appropriate RHS predicate for this LHS,
4764    before the LHS has been gimplified.  */
4765 
4766 static gimple_predicate
initial_rhs_predicate_for(tree lhs)4767 initial_rhs_predicate_for (tree lhs)
4768 {
4769   if (is_gimple_reg_type (TREE_TYPE (lhs)))
4770     return is_gimple_reg_rhs_or_call;
4771   else
4772     return is_gimple_mem_rhs_or_call;
4773 }
4774 
4775 /* Gimplify a C99 compound literal expression.  This just means adding
4776    the DECL_EXPR before the current statement and using its anonymous
4777    decl instead.  */
4778 
4779 static enum gimplify_status
gimplify_compound_literal_expr(tree * expr_p,gimple_seq * pre_p,bool (* gimple_test_f)(tree),fallback_t fallback)4780 gimplify_compound_literal_expr (tree *expr_p, gimple_seq *pre_p,
4781 				bool (*gimple_test_f) (tree),
4782 				fallback_t fallback)
4783 {
4784   tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (*expr_p);
4785   tree decl = DECL_EXPR_DECL (decl_s);
4786   tree init = DECL_INITIAL (decl);
4787   /* Mark the decl as addressable if the compound literal
4788      expression is addressable now, otherwise it is marked too late
4789      after we gimplify the initialization expression.  */
4790   if (TREE_ADDRESSABLE (*expr_p))
4791     TREE_ADDRESSABLE (decl) = 1;
4792   /* Otherwise, if we don't need an lvalue and have a literal directly
4793      substitute it.  Check if it matches the gimple predicate, as
4794      otherwise we'd generate a new temporary, and we can as well just
4795      use the decl we already have.  */
4796   else if (!TREE_ADDRESSABLE (decl)
4797 	   && !TREE_THIS_VOLATILE (decl)
4798 	   && init
4799 	   && (fallback & fb_lvalue) == 0
4800 	   && gimple_test_f (init))
4801     {
4802       *expr_p = init;
4803       return GS_OK;
4804     }
4805 
4806   /* If the decl is not addressable, then it is being used in some
4807      expression or on the right hand side of a statement, and it can
4808      be put into a readonly data section.  */
4809   if (!TREE_ADDRESSABLE (decl) && (fallback & fb_lvalue) == 0)
4810     TREE_READONLY (decl) = 1;
4811 
4812   /* This decl isn't mentioned in the enclosing block, so add it to the
4813      list of temps.  FIXME it seems a bit of a kludge to say that
4814      anonymous artificial vars aren't pushed, but everything else is.  */
4815   if (DECL_NAME (decl) == NULL_TREE && !DECL_SEEN_IN_BIND_EXPR_P (decl))
4816     gimple_add_tmp_var (decl);
4817 
4818   gimplify_and_add (decl_s, pre_p);
4819   *expr_p = decl;
4820   return GS_OK;
4821 }
4822 
4823 /* Optimize embedded COMPOUND_LITERAL_EXPRs within a CONSTRUCTOR,
4824    return a new CONSTRUCTOR if something changed.  */
4825 
4826 static tree
optimize_compound_literals_in_ctor(tree orig_ctor)4827 optimize_compound_literals_in_ctor (tree orig_ctor)
4828 {
4829   tree ctor = orig_ctor;
4830   vec<constructor_elt, va_gc> *elts = CONSTRUCTOR_ELTS (ctor);
4831   unsigned int idx, num = vec_safe_length (elts);
4832 
4833   for (idx = 0; idx < num; idx++)
4834     {
4835       tree value = (*elts)[idx].value;
4836       tree newval = value;
4837       if (TREE_CODE (value) == CONSTRUCTOR)
4838 	newval = optimize_compound_literals_in_ctor (value);
4839       else if (TREE_CODE (value) == COMPOUND_LITERAL_EXPR)
4840 	{
4841 	  tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (value);
4842 	  tree decl = DECL_EXPR_DECL (decl_s);
4843 	  tree init = DECL_INITIAL (decl);
4844 
4845 	  if (!TREE_ADDRESSABLE (value)
4846 	      && !TREE_ADDRESSABLE (decl)
4847 	      && init
4848 	      && TREE_CODE (init) == CONSTRUCTOR)
4849 	    newval = optimize_compound_literals_in_ctor (init);
4850 	}
4851       if (newval == value)
4852 	continue;
4853 
4854       if (ctor == orig_ctor)
4855 	{
4856 	  ctor = copy_node (orig_ctor);
4857 	  CONSTRUCTOR_ELTS (ctor) = vec_safe_copy (elts);
4858 	  elts = CONSTRUCTOR_ELTS (ctor);
4859 	}
4860       (*elts)[idx].value = newval;
4861     }
4862   return ctor;
4863 }
4864 
4865 /* A subroutine of gimplify_modify_expr.  Break out elements of a
4866    CONSTRUCTOR used as an initializer into separate MODIFY_EXPRs.
4867 
4868    Note that we still need to clear any elements that don't have explicit
4869    initializers, so if not all elements are initialized we keep the
4870    original MODIFY_EXPR, we just remove all of the constructor elements.
4871 
4872    If NOTIFY_TEMP_CREATION is true, do not gimplify, just return
4873    GS_ERROR if we would have to create a temporary when gimplifying
4874    this constructor.  Otherwise, return GS_OK.
4875 
4876    If NOTIFY_TEMP_CREATION is false, just do the gimplification.  */
4877 
4878 static enum gimplify_status
gimplify_init_constructor(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,bool want_value,bool notify_temp_creation)4879 gimplify_init_constructor (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
4880 			   bool want_value, bool notify_temp_creation)
4881 {
4882   tree object, ctor, type;
4883   enum gimplify_status ret;
4884   vec<constructor_elt, va_gc> *elts;
4885 
4886   gcc_assert (TREE_CODE (TREE_OPERAND (*expr_p, 1)) == CONSTRUCTOR);
4887 
4888   if (!notify_temp_creation)
4889     {
4890       ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
4891 			   is_gimple_lvalue, fb_lvalue);
4892       if (ret == GS_ERROR)
4893 	return ret;
4894     }
4895 
4896   object = TREE_OPERAND (*expr_p, 0);
4897   ctor = TREE_OPERAND (*expr_p, 1)
4898     = optimize_compound_literals_in_ctor (TREE_OPERAND (*expr_p, 1));
4899   type = TREE_TYPE (ctor);
4900   elts = CONSTRUCTOR_ELTS (ctor);
4901   ret = GS_ALL_DONE;
4902 
4903   switch (TREE_CODE (type))
4904     {
4905     case RECORD_TYPE:
4906     case UNION_TYPE:
4907     case QUAL_UNION_TYPE:
4908     case ARRAY_TYPE:
4909       {
4910 	/* Use readonly data for initializers of this or smaller size
4911 	   regardless of the num_nonzero_elements / num_unique_nonzero_elements
4912 	   ratio.  */
4913 	const HOST_WIDE_INT min_unique_size = 64;
4914 	/* If num_nonzero_elements / num_unique_nonzero_elements ratio
4915 	   is smaller than this, use readonly data.  */
4916 	const int unique_nonzero_ratio = 8;
4917 	/* True if a single access of the object must be ensured.  This is the
4918 	   case if the target is volatile, the type is non-addressable and more
4919 	   than one field need to be assigned.  */
4920 	const bool ensure_single_access
4921 	  = TREE_THIS_VOLATILE (object)
4922 	    && !TREE_ADDRESSABLE (type)
4923 	    && vec_safe_length (elts) > 1;
4924 	struct gimplify_init_ctor_preeval_data preeval_data;
4925 	HOST_WIDE_INT num_ctor_elements, num_nonzero_elements;
4926 	HOST_WIDE_INT num_unique_nonzero_elements;
4927 	bool cleared, complete_p, valid_const_initializer;
4928 
4929 	/* Aggregate types must lower constructors to initialization of
4930 	   individual elements.  The exception is that a CONSTRUCTOR node
4931 	   with no elements indicates zero-initialization of the whole.  */
4932 	if (vec_safe_is_empty (elts))
4933 	  {
4934 	    if (notify_temp_creation)
4935 	      return GS_OK;
4936 	    break;
4937 	  }
4938 
4939 	/* Fetch information about the constructor to direct later processing.
4940 	   We might want to make static versions of it in various cases, and
4941 	   can only do so if it known to be a valid constant initializer.  */
4942 	valid_const_initializer
4943 	  = categorize_ctor_elements (ctor, &num_nonzero_elements,
4944 				      &num_unique_nonzero_elements,
4945 				      &num_ctor_elements, &complete_p);
4946 
4947 	/* If a const aggregate variable is being initialized, then it
4948 	   should never be a lose to promote the variable to be static.  */
4949 	if (valid_const_initializer
4950 	    && num_nonzero_elements > 1
4951 	    && TREE_READONLY (object)
4952 	    && VAR_P (object)
4953 	    && !DECL_REGISTER (object)
4954 	    && (flag_merge_constants >= 2 || !TREE_ADDRESSABLE (object))
4955 	    /* For ctors that have many repeated nonzero elements
4956 	       represented through RANGE_EXPRs, prefer initializing
4957 	       those through runtime loops over copies of large amounts
4958 	       of data from readonly data section.  */
4959 	    && (num_unique_nonzero_elements
4960 		> num_nonzero_elements / unique_nonzero_ratio
4961 		|| ((unsigned HOST_WIDE_INT) int_size_in_bytes (type)
4962 		    <= (unsigned HOST_WIDE_INT) min_unique_size)))
4963 	  {
4964 	    if (notify_temp_creation)
4965 	      return GS_ERROR;
4966 
4967 	    DECL_INITIAL (object) = ctor;
4968 	    TREE_STATIC (object) = 1;
4969 	    if (!DECL_NAME (object))
4970 	      DECL_NAME (object) = create_tmp_var_name ("C");
4971 	    walk_tree (&DECL_INITIAL (object), force_labels_r, NULL, NULL);
4972 
4973 	    /* ??? C++ doesn't automatically append a .<number> to the
4974 	       assembler name, and even when it does, it looks at FE private
4975 	       data structures to figure out what that number should be,
4976 	       which are not set for this variable.  I suppose this is
4977 	       important for local statics for inline functions, which aren't
4978 	       "local" in the object file sense.  So in order to get a unique
4979 	       TU-local symbol, we must invoke the lhd version now.  */
4980 	    lhd_set_decl_assembler_name (object);
4981 
4982 	    *expr_p = NULL_TREE;
4983 	    break;
4984 	  }
4985 
4986 	/* If there are "lots" of initialized elements, even discounting
4987 	   those that are not address constants (and thus *must* be
4988 	   computed at runtime), then partition the constructor into
4989 	   constant and non-constant parts.  Block copy the constant
4990 	   parts in, then generate code for the non-constant parts.  */
4991 	/* TODO.  There's code in cp/typeck.c to do this.  */
4992 
4993 	if (int_size_in_bytes (TREE_TYPE (ctor)) < 0)
4994 	  /* store_constructor will ignore the clearing of variable-sized
4995 	     objects.  Initializers for such objects must explicitly set
4996 	     every field that needs to be set.  */
4997 	  cleared = false;
4998 	else if (!complete_p)
4999 	  /* If the constructor isn't complete, clear the whole object
5000 	     beforehand, unless CONSTRUCTOR_NO_CLEARING is set on it.
5001 
5002 	     ??? This ought not to be needed.  For any element not present
5003 	     in the initializer, we should simply set them to zero.  Except
5004 	     we'd need to *find* the elements that are not present, and that
5005 	     requires trickery to avoid quadratic compile-time behavior in
5006 	     large cases or excessive memory use in small cases.  */
5007 	  cleared = !CONSTRUCTOR_NO_CLEARING (ctor);
5008 	else if (num_ctor_elements - num_nonzero_elements
5009 		 > CLEAR_RATIO (optimize_function_for_speed_p (cfun))
5010 		 && num_nonzero_elements < num_ctor_elements / 4)
5011 	  /* If there are "lots" of zeros, it's more efficient to clear
5012 	     the memory and then set the nonzero elements.  */
5013 	  cleared = true;
5014 	else if (ensure_single_access && num_nonzero_elements == 0)
5015 	  /* If a single access to the target must be ensured and all elements
5016 	     are zero, then it's optimal to clear whatever their number.  */
5017 	  cleared = true;
5018 	else
5019 	  cleared = false;
5020 
5021 	/* If there are "lots" of initialized elements, and all of them
5022 	   are valid address constants, then the entire initializer can
5023 	   be dropped to memory, and then memcpy'd out.  Don't do this
5024 	   for sparse arrays, though, as it's more efficient to follow
5025 	   the standard CONSTRUCTOR behavior of memset followed by
5026 	   individual element initialization.  Also don't do this for small
5027 	   all-zero initializers (which aren't big enough to merit
5028 	   clearing), and don't try to make bitwise copies of
5029 	   TREE_ADDRESSABLE types.  */
5030 	if (valid_const_initializer
5031 	    && complete_p
5032 	    && !(cleared || num_nonzero_elements == 0)
5033 	    && !TREE_ADDRESSABLE (type))
5034 	  {
5035 	    HOST_WIDE_INT size = int_size_in_bytes (type);
5036 	    unsigned int align;
5037 
5038 	    /* ??? We can still get unbounded array types, at least
5039 	       from the C++ front end.  This seems wrong, but attempt
5040 	       to work around it for now.  */
5041 	    if (size < 0)
5042 	      {
5043 		size = int_size_in_bytes (TREE_TYPE (object));
5044 		if (size >= 0)
5045 		  TREE_TYPE (ctor) = type = TREE_TYPE (object);
5046 	      }
5047 
5048 	    /* Find the maximum alignment we can assume for the object.  */
5049 	    /* ??? Make use of DECL_OFFSET_ALIGN.  */
5050 	    if (DECL_P (object))
5051 	      align = DECL_ALIGN (object);
5052 	    else
5053 	      align = TYPE_ALIGN (type);
5054 
5055 	    /* Do a block move either if the size is so small as to make
5056 	       each individual move a sub-unit move on average, or if it
5057 	       is so large as to make individual moves inefficient.  */
5058 	    if (size > 0
5059 		&& num_nonzero_elements > 1
5060 		/* For ctors that have many repeated nonzero elements
5061 		   represented through RANGE_EXPRs, prefer initializing
5062 		   those through runtime loops over copies of large amounts
5063 		   of data from readonly data section.  */
5064 		&& (num_unique_nonzero_elements
5065 		    > num_nonzero_elements / unique_nonzero_ratio
5066 		    || size <= min_unique_size)
5067 		&& (size < num_nonzero_elements
5068 		    || !can_move_by_pieces (size, align)))
5069 	      {
5070 		if (notify_temp_creation)
5071 		  return GS_ERROR;
5072 
5073 		walk_tree (&ctor, force_labels_r, NULL, NULL);
5074 		ctor = tree_output_constant_def (ctor);
5075 		if (!useless_type_conversion_p (type, TREE_TYPE (ctor)))
5076 		  ctor = build1 (VIEW_CONVERT_EXPR, type, ctor);
5077 		TREE_OPERAND (*expr_p, 1) = ctor;
5078 
5079 		/* This is no longer an assignment of a CONSTRUCTOR, but
5080 		   we still may have processing to do on the LHS.  So
5081 		   pretend we didn't do anything here to let that happen.  */
5082 		return GS_UNHANDLED;
5083 	      }
5084 	  }
5085 
5086 	/* If a single access to the target must be ensured and there are
5087 	   nonzero elements or the zero elements are not assigned en masse,
5088 	   initialize the target from a temporary.  */
5089 	if (ensure_single_access && (num_nonzero_elements > 0 || !cleared))
5090 	  {
5091 	    if (notify_temp_creation)
5092 	      return GS_ERROR;
5093 
5094 	    tree temp = create_tmp_var (TYPE_MAIN_VARIANT (type));
5095 	    TREE_OPERAND (*expr_p, 0) = temp;
5096 	    *expr_p = build2 (COMPOUND_EXPR, TREE_TYPE (*expr_p),
5097 			      *expr_p,
5098 			      build2 (MODIFY_EXPR, void_type_node,
5099 				      object, temp));
5100 	    return GS_OK;
5101 	  }
5102 
5103 	if (notify_temp_creation)
5104 	  return GS_OK;
5105 
5106 	/* If there are nonzero elements and if needed, pre-evaluate to capture
5107 	   elements overlapping with the lhs into temporaries.  We must do this
5108 	   before clearing to fetch the values before they are zeroed-out.  */
5109 	if (num_nonzero_elements > 0 && TREE_CODE (*expr_p) != INIT_EXPR)
5110 	  {
5111 	    preeval_data.lhs_base_decl = get_base_address (object);
5112 	    if (!DECL_P (preeval_data.lhs_base_decl))
5113 	      preeval_data.lhs_base_decl = NULL;
5114 	    preeval_data.lhs_alias_set = get_alias_set (object);
5115 
5116 	    gimplify_init_ctor_preeval (&TREE_OPERAND (*expr_p, 1),
5117 					pre_p, post_p, &preeval_data);
5118 	  }
5119 
5120 	bool ctor_has_side_effects_p
5121 	  = TREE_SIDE_EFFECTS (TREE_OPERAND (*expr_p, 1));
5122 
5123 	if (cleared)
5124 	  {
5125 	    /* Zap the CONSTRUCTOR element list, which simplifies this case.
5126 	       Note that we still have to gimplify, in order to handle the
5127 	       case of variable sized types.  Avoid shared tree structures.  */
5128 	    CONSTRUCTOR_ELTS (ctor) = NULL;
5129 	    TREE_SIDE_EFFECTS (ctor) = 0;
5130 	    object = unshare_expr (object);
5131 	    gimplify_stmt (expr_p, pre_p);
5132 	  }
5133 
5134 	/* If we have not block cleared the object, or if there are nonzero
5135 	   elements in the constructor, or if the constructor has side effects,
5136 	   add assignments to the individual scalar fields of the object.  */
5137 	if (!cleared
5138 	    || num_nonzero_elements > 0
5139 	    || ctor_has_side_effects_p)
5140 	  gimplify_init_ctor_eval (object, elts, pre_p, cleared);
5141 
5142 	*expr_p = NULL_TREE;
5143       }
5144       break;
5145 
5146     case COMPLEX_TYPE:
5147       {
5148 	tree r, i;
5149 
5150 	if (notify_temp_creation)
5151 	  return GS_OK;
5152 
5153 	/* Extract the real and imaginary parts out of the ctor.  */
5154 	gcc_assert (elts->length () == 2);
5155 	r = (*elts)[0].value;
5156 	i = (*elts)[1].value;
5157 	if (r == NULL || i == NULL)
5158 	  {
5159 	    tree zero = build_zero_cst (TREE_TYPE (type));
5160 	    if (r == NULL)
5161 	      r = zero;
5162 	    if (i == NULL)
5163 	      i = zero;
5164 	  }
5165 
5166 	/* Complex types have either COMPLEX_CST or COMPLEX_EXPR to
5167 	   represent creation of a complex value.  */
5168 	if (TREE_CONSTANT (r) && TREE_CONSTANT (i))
5169 	  {
5170 	    ctor = build_complex (type, r, i);
5171 	    TREE_OPERAND (*expr_p, 1) = ctor;
5172 	  }
5173 	else
5174 	  {
5175 	    ctor = build2 (COMPLEX_EXPR, type, r, i);
5176 	    TREE_OPERAND (*expr_p, 1) = ctor;
5177 	    ret = gimplify_expr (&TREE_OPERAND (*expr_p, 1),
5178 				 pre_p,
5179 				 post_p,
5180 				 rhs_predicate_for (TREE_OPERAND (*expr_p, 0)),
5181 				 fb_rvalue);
5182 	  }
5183       }
5184       break;
5185 
5186     case VECTOR_TYPE:
5187       {
5188 	unsigned HOST_WIDE_INT ix;
5189 	constructor_elt *ce;
5190 
5191 	if (notify_temp_creation)
5192 	  return GS_OK;
5193 
5194 	/* Go ahead and simplify constant constructors to VECTOR_CST.  */
5195 	if (TREE_CONSTANT (ctor))
5196 	  {
5197 	    bool constant_p = true;
5198 	    tree value;
5199 
5200 	    /* Even when ctor is constant, it might contain non-*_CST
5201 	       elements, such as addresses or trapping values like
5202 	       1.0/0.0 - 1.0/0.0.  Such expressions don't belong
5203 	       in VECTOR_CST nodes.  */
5204 	    FOR_EACH_CONSTRUCTOR_VALUE (elts, ix, value)
5205 	      if (!CONSTANT_CLASS_P (value))
5206 		{
5207 		  constant_p = false;
5208 		  break;
5209 		}
5210 
5211 	    if (constant_p)
5212 	      {
5213 		TREE_OPERAND (*expr_p, 1) = build_vector_from_ctor (type, elts);
5214 		break;
5215 	      }
5216 
5217 	    TREE_CONSTANT (ctor) = 0;
5218 	  }
5219 
5220 	/* Vector types use CONSTRUCTOR all the way through gimple
5221 	   compilation as a general initializer.  */
5222 	FOR_EACH_VEC_SAFE_ELT (elts, ix, ce)
5223 	  {
5224 	    enum gimplify_status tret;
5225 	    tret = gimplify_expr (&ce->value, pre_p, post_p, is_gimple_val,
5226 				  fb_rvalue);
5227 	    if (tret == GS_ERROR)
5228 	      ret = GS_ERROR;
5229 	    else if (TREE_STATIC (ctor)
5230 		     && !initializer_constant_valid_p (ce->value,
5231 						       TREE_TYPE (ce->value)))
5232 	      TREE_STATIC (ctor) = 0;
5233 	  }
5234 	recompute_constructor_flags (ctor);
5235 	if (!is_gimple_reg (TREE_OPERAND (*expr_p, 0)))
5236 	  TREE_OPERAND (*expr_p, 1) = get_formal_tmp_var (ctor, pre_p);
5237       }
5238       break;
5239 
5240     default:
5241       /* So how did we get a CONSTRUCTOR for a scalar type?  */
5242       gcc_unreachable ();
5243     }
5244 
5245   if (ret == GS_ERROR)
5246     return GS_ERROR;
5247   /* If we have gimplified both sides of the initializer but have
5248      not emitted an assignment, do so now.  */
5249   if (*expr_p)
5250     {
5251       tree lhs = TREE_OPERAND (*expr_p, 0);
5252       tree rhs = TREE_OPERAND (*expr_p, 1);
5253       if (want_value && object == lhs)
5254 	lhs = unshare_expr (lhs);
5255       gassign *init = gimple_build_assign (lhs, rhs);
5256       gimplify_seq_add_stmt (pre_p, init);
5257     }
5258   if (want_value)
5259     {
5260       *expr_p = object;
5261       return GS_OK;
5262     }
5263   else
5264     {
5265       *expr_p = NULL;
5266       return GS_ALL_DONE;
5267     }
5268 }
5269 
5270 /* Given a pointer value OP0, return a simplified version of an
5271    indirection through OP0, or NULL_TREE if no simplification is
5272    possible.  This may only be applied to a rhs of an expression.
5273    Note that the resulting type may be different from the type pointed
5274    to in the sense that it is still compatible from the langhooks
5275    point of view. */
5276 
5277 static tree
gimple_fold_indirect_ref_rhs(tree t)5278 gimple_fold_indirect_ref_rhs (tree t)
5279 {
5280   return gimple_fold_indirect_ref (t);
5281 }
5282 
5283 /* Subroutine of gimplify_modify_expr to do simplifications of
5284    MODIFY_EXPRs based on the code of the RHS.  We loop for as long as
5285    something changes.  */
5286 
5287 static enum gimplify_status
gimplify_modify_expr_rhs(tree * expr_p,tree * from_p,tree * to_p,gimple_seq * pre_p,gimple_seq * post_p,bool want_value)5288 gimplify_modify_expr_rhs (tree *expr_p, tree *from_p, tree *to_p,
5289 			  gimple_seq *pre_p, gimple_seq *post_p,
5290 			  bool want_value)
5291 {
5292   enum gimplify_status ret = GS_UNHANDLED;
5293   bool changed;
5294 
5295   do
5296     {
5297       changed = false;
5298       switch (TREE_CODE (*from_p))
5299 	{
5300 	case VAR_DECL:
5301 	  /* If we're assigning from a read-only variable initialized with
5302 	     a constructor and not volatile, do the direct assignment from
5303 	     the constructor, but only if the target is not volatile either
5304 	     since this latter assignment might end up being done on a per
5305 	     field basis.  However, if the target is volatile and the type
5306 	     is aggregate and non-addressable, gimplify_init_constructor
5307 	     knows that it needs to ensure a single access to the target
5308 	     and it will return GS_OK only in this case.  */
5309 	  if (TREE_READONLY (*from_p)
5310 	      && DECL_INITIAL (*from_p)
5311 	      && TREE_CODE (DECL_INITIAL (*from_p)) == CONSTRUCTOR
5312 	      && !TREE_THIS_VOLATILE (*from_p)
5313 	      && (!TREE_THIS_VOLATILE (*to_p)
5314 		  || (AGGREGATE_TYPE_P (TREE_TYPE (*to_p))
5315 		      && !TREE_ADDRESSABLE (TREE_TYPE (*to_p)))))
5316 	    {
5317 	      tree old_from = *from_p;
5318 	      enum gimplify_status subret;
5319 
5320 	      /* Move the constructor into the RHS.  */
5321 	      *from_p = unshare_expr (DECL_INITIAL (*from_p));
5322 
5323 	      /* Let's see if gimplify_init_constructor will need to put
5324 		 it in memory.  */
5325 	      subret = gimplify_init_constructor (expr_p, NULL, NULL,
5326 						  false, true);
5327 	      if (subret == GS_ERROR)
5328 		{
5329 		  /* If so, revert the change.  */
5330 		  *from_p = old_from;
5331 		}
5332 	      else
5333 		{
5334 		  ret = GS_OK;
5335 		  changed = true;
5336 		}
5337 	    }
5338 	  break;
5339 	case INDIRECT_REF:
5340 	  {
5341 	    /* If we have code like
5342 
5343 	     *(const A*)(A*)&x
5344 
5345 	     where the type of "x" is a (possibly cv-qualified variant
5346 	     of "A"), treat the entire expression as identical to "x".
5347 	     This kind of code arises in C++ when an object is bound
5348 	     to a const reference, and if "x" is a TARGET_EXPR we want
5349 	     to take advantage of the optimization below.  */
5350 	    bool volatile_p = TREE_THIS_VOLATILE (*from_p);
5351 	    tree t = gimple_fold_indirect_ref_rhs (TREE_OPERAND (*from_p, 0));
5352 	    if (t)
5353 	      {
5354 		if (TREE_THIS_VOLATILE (t) != volatile_p)
5355 		  {
5356 		    if (DECL_P (t))
5357 		      t = build_simple_mem_ref_loc (EXPR_LOCATION (*from_p),
5358 						    build_fold_addr_expr (t));
5359 		    if (REFERENCE_CLASS_P (t))
5360 		      TREE_THIS_VOLATILE (t) = volatile_p;
5361 		  }
5362 		*from_p = t;
5363 		ret = GS_OK;
5364 		changed = true;
5365 	      }
5366 	    break;
5367 	  }
5368 
5369 	case TARGET_EXPR:
5370 	  {
5371 	    /* If we are initializing something from a TARGET_EXPR, strip the
5372 	       TARGET_EXPR and initialize it directly, if possible.  This can't
5373 	       be done if the initializer is void, since that implies that the
5374 	       temporary is set in some non-trivial way.
5375 
5376 	       ??? What about code that pulls out the temp and uses it
5377 	       elsewhere? I think that such code never uses the TARGET_EXPR as
5378 	       an initializer.  If I'm wrong, we'll die because the temp won't
5379 	       have any RTL.  In that case, I guess we'll need to replace
5380 	       references somehow.  */
5381 	    tree init = TARGET_EXPR_INITIAL (*from_p);
5382 
5383 	    if (init
5384 		&& (TREE_CODE (*expr_p) != MODIFY_EXPR
5385 		    || !TARGET_EXPR_NO_ELIDE (*from_p))
5386 		&& !VOID_TYPE_P (TREE_TYPE (init)))
5387 	      {
5388 		*from_p = init;
5389 		ret = GS_OK;
5390 		changed = true;
5391 	      }
5392 	  }
5393 	  break;
5394 
5395 	case COMPOUND_EXPR:
5396 	  /* Remove any COMPOUND_EXPR in the RHS so the following cases will be
5397 	     caught.  */
5398 	  gimplify_compound_expr (from_p, pre_p, true);
5399 	  ret = GS_OK;
5400 	  changed = true;
5401 	  break;
5402 
5403 	case CONSTRUCTOR:
5404 	  /* If we already made some changes, let the front end have a
5405 	     crack at this before we break it down.  */
5406 	  if (ret != GS_UNHANDLED)
5407 	    break;
5408 	  /* If we're initializing from a CONSTRUCTOR, break this into
5409 	     individual MODIFY_EXPRs.  */
5410 	  return gimplify_init_constructor (expr_p, pre_p, post_p, want_value,
5411 					    false);
5412 
5413 	case COND_EXPR:
5414 	  /* If we're assigning to a non-register type, push the assignment
5415 	     down into the branches.  This is mandatory for ADDRESSABLE types,
5416 	     since we cannot generate temporaries for such, but it saves a
5417 	     copy in other cases as well.  */
5418 	  if (!is_gimple_reg_type (TREE_TYPE (*from_p)))
5419 	    {
5420 	      /* This code should mirror the code in gimplify_cond_expr. */
5421 	      enum tree_code code = TREE_CODE (*expr_p);
5422 	      tree cond = *from_p;
5423 	      tree result = *to_p;
5424 
5425 	      ret = gimplify_expr (&result, pre_p, post_p,
5426 				   is_gimple_lvalue, fb_lvalue);
5427 	      if (ret != GS_ERROR)
5428 		ret = GS_OK;
5429 
5430 	      /* If we are going to write RESULT more than once, clear
5431 		 TREE_READONLY flag, otherwise we might incorrectly promote
5432 		 the variable to static const and initialize it at compile
5433 		 time in one of the branches.  */
5434 	      if (VAR_P (result)
5435 		  && TREE_TYPE (TREE_OPERAND (cond, 1)) != void_type_node
5436 		  && TREE_TYPE (TREE_OPERAND (cond, 2)) != void_type_node)
5437 		TREE_READONLY (result) = 0;
5438 	      if (TREE_TYPE (TREE_OPERAND (cond, 1)) != void_type_node)
5439 		TREE_OPERAND (cond, 1)
5440 		  = build2 (code, void_type_node, result,
5441 			    TREE_OPERAND (cond, 1));
5442 	      if (TREE_TYPE (TREE_OPERAND (cond, 2)) != void_type_node)
5443 		TREE_OPERAND (cond, 2)
5444 		  = build2 (code, void_type_node, unshare_expr (result),
5445 			    TREE_OPERAND (cond, 2));
5446 
5447 	      TREE_TYPE (cond) = void_type_node;
5448 	      recalculate_side_effects (cond);
5449 
5450 	      if (want_value)
5451 		{
5452 		  gimplify_and_add (cond, pre_p);
5453 		  *expr_p = unshare_expr (result);
5454 		}
5455 	      else
5456 		*expr_p = cond;
5457 	      return ret;
5458 	    }
5459 	  break;
5460 
5461 	case CALL_EXPR:
5462 	  /* For calls that return in memory, give *to_p as the CALL_EXPR's
5463 	     return slot so that we don't generate a temporary.  */
5464 	  if (!CALL_EXPR_RETURN_SLOT_OPT (*from_p)
5465 	      && aggregate_value_p (*from_p, *from_p))
5466 	    {
5467 	      bool use_target;
5468 
5469 	      if (!(rhs_predicate_for (*to_p))(*from_p))
5470 		/* If we need a temporary, *to_p isn't accurate.  */
5471 		use_target = false;
5472 	      /* It's OK to use the return slot directly unless it's an NRV. */
5473 	      else if (TREE_CODE (*to_p) == RESULT_DECL
5474 		       && DECL_NAME (*to_p) == NULL_TREE
5475 		       && needs_to_live_in_memory (*to_p))
5476 		use_target = true;
5477 	      else if (is_gimple_reg_type (TREE_TYPE (*to_p))
5478 		       || (DECL_P (*to_p) && DECL_REGISTER (*to_p)))
5479 		/* Don't force regs into memory.  */
5480 		use_target = false;
5481 	      else if (TREE_CODE (*expr_p) == INIT_EXPR)
5482 		/* It's OK to use the target directly if it's being
5483 		   initialized. */
5484 		use_target = true;
5485 	      else if (TREE_CODE (TYPE_SIZE_UNIT (TREE_TYPE (*to_p)))
5486 		       != INTEGER_CST)
5487 		/* Always use the target and thus RSO for variable-sized types.
5488 		   GIMPLE cannot deal with a variable-sized assignment
5489 		   embedded in a call statement.  */
5490 		use_target = true;
5491 	      else if (TREE_CODE (*to_p) != SSA_NAME
5492 		      && (!is_gimple_variable (*to_p)
5493 			  || needs_to_live_in_memory (*to_p)))
5494 		/* Don't use the original target if it's already addressable;
5495 		   if its address escapes, and the called function uses the
5496 		   NRV optimization, a conforming program could see *to_p
5497 		   change before the called function returns; see c++/19317.
5498 		   When optimizing, the return_slot pass marks more functions
5499 		   as safe after we have escape info.  */
5500 		use_target = false;
5501 	      else
5502 		use_target = true;
5503 
5504 	      if (use_target)
5505 		{
5506 		  CALL_EXPR_RETURN_SLOT_OPT (*from_p) = 1;
5507 		  mark_addressable (*to_p);
5508 		}
5509 	    }
5510 	  break;
5511 
5512 	case WITH_SIZE_EXPR:
5513 	  /* Likewise for calls that return an aggregate of non-constant size,
5514 	     since we would not be able to generate a temporary at all.  */
5515 	  if (TREE_CODE (TREE_OPERAND (*from_p, 0)) == CALL_EXPR)
5516 	    {
5517 	      *from_p = TREE_OPERAND (*from_p, 0);
5518 	      /* We don't change ret in this case because the
5519 		 WITH_SIZE_EXPR might have been added in
5520 		 gimplify_modify_expr, so returning GS_OK would lead to an
5521 		 infinite loop.  */
5522 	      changed = true;
5523 	    }
5524 	  break;
5525 
5526 	  /* If we're initializing from a container, push the initialization
5527 	     inside it.  */
5528 	case CLEANUP_POINT_EXPR:
5529 	case BIND_EXPR:
5530 	case STATEMENT_LIST:
5531 	  {
5532 	    tree wrap = *from_p;
5533 	    tree t;
5534 
5535 	    ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_min_lval,
5536 				 fb_lvalue);
5537 	    if (ret != GS_ERROR)
5538 	      ret = GS_OK;
5539 
5540 	    t = voidify_wrapper_expr (wrap, *expr_p);
5541 	    gcc_assert (t == *expr_p);
5542 
5543 	    if (want_value)
5544 	      {
5545 		gimplify_and_add (wrap, pre_p);
5546 		*expr_p = unshare_expr (*to_p);
5547 	      }
5548 	    else
5549 	      *expr_p = wrap;
5550 	    return GS_OK;
5551 	  }
5552 
5553 	case NOP_EXPR:
5554 	  /* Pull out compound literal expressions from a NOP_EXPR.
5555 	     Those are created in the C FE to drop qualifiers during
5556 	     lvalue conversion.  */
5557 	  if ((TREE_CODE (TREE_OPERAND (*from_p, 0)) == COMPOUND_LITERAL_EXPR)
5558 	      && tree_ssa_useless_type_conversion (*from_p))
5559 	    {
5560 	      *from_p = TREE_OPERAND (*from_p, 0);
5561 	      ret = GS_OK;
5562 	      changed = true;
5563 	    }
5564 	  break;
5565 
5566 	case COMPOUND_LITERAL_EXPR:
5567 	  {
5568 	    tree complit = TREE_OPERAND (*expr_p, 1);
5569 	    tree decl_s = COMPOUND_LITERAL_EXPR_DECL_EXPR (complit);
5570 	    tree decl = DECL_EXPR_DECL (decl_s);
5571 	    tree init = DECL_INITIAL (decl);
5572 
5573 	    /* struct T x = (struct T) { 0, 1, 2 } can be optimized
5574 	       into struct T x = { 0, 1, 2 } if the address of the
5575 	       compound literal has never been taken.  */
5576 	    if (!TREE_ADDRESSABLE (complit)
5577 		&& !TREE_ADDRESSABLE (decl)
5578 		&& init)
5579 	      {
5580 		*expr_p = copy_node (*expr_p);
5581 		TREE_OPERAND (*expr_p, 1) = init;
5582 		return GS_OK;
5583 	      }
5584 	  }
5585 
5586 	default:
5587 	  break;
5588 	}
5589     }
5590   while (changed);
5591 
5592   return ret;
5593 }
5594 
5595 
5596 /* Return true if T looks like a valid GIMPLE statement.  */
5597 
5598 static bool
is_gimple_stmt(tree t)5599 is_gimple_stmt (tree t)
5600 {
5601   const enum tree_code code = TREE_CODE (t);
5602 
5603   switch (code)
5604     {
5605     case NOP_EXPR:
5606       /* The only valid NOP_EXPR is the empty statement.  */
5607       return IS_EMPTY_STMT (t);
5608 
5609     case BIND_EXPR:
5610     case COND_EXPR:
5611       /* These are only valid if they're void.  */
5612       return TREE_TYPE (t) == NULL || VOID_TYPE_P (TREE_TYPE (t));
5613 
5614     case SWITCH_EXPR:
5615     case GOTO_EXPR:
5616     case RETURN_EXPR:
5617     case LABEL_EXPR:
5618     case CASE_LABEL_EXPR:
5619     case TRY_CATCH_EXPR:
5620     case TRY_FINALLY_EXPR:
5621     case EH_FILTER_EXPR:
5622     case CATCH_EXPR:
5623     case ASM_EXPR:
5624     case STATEMENT_LIST:
5625     case OACC_PARALLEL:
5626     case OACC_KERNELS:
5627     case OACC_SERIAL:
5628     case OACC_DATA:
5629     case OACC_HOST_DATA:
5630     case OACC_DECLARE:
5631     case OACC_UPDATE:
5632     case OACC_ENTER_DATA:
5633     case OACC_EXIT_DATA:
5634     case OACC_CACHE:
5635     case OMP_PARALLEL:
5636     case OMP_FOR:
5637     case OMP_SIMD:
5638     case OMP_DISTRIBUTE:
5639     case OMP_LOOP:
5640     case OACC_LOOP:
5641     case OMP_SCAN:
5642     case OMP_SECTIONS:
5643     case OMP_SECTION:
5644     case OMP_SINGLE:
5645     case OMP_MASTER:
5646     case OMP_TASKGROUP:
5647     case OMP_ORDERED:
5648     case OMP_CRITICAL:
5649     case OMP_TASK:
5650     case OMP_TARGET:
5651     case OMP_TARGET_DATA:
5652     case OMP_TARGET_UPDATE:
5653     case OMP_TARGET_ENTER_DATA:
5654     case OMP_TARGET_EXIT_DATA:
5655     case OMP_TASKLOOP:
5656     case OMP_TEAMS:
5657       /* These are always void.  */
5658       return true;
5659 
5660     case CALL_EXPR:
5661     case MODIFY_EXPR:
5662     case PREDICT_EXPR:
5663       /* These are valid regardless of their type.  */
5664       return true;
5665 
5666     default:
5667       return false;
5668     }
5669 }
5670 
5671 
5672 /* Promote partial stores to COMPLEX variables to total stores.  *EXPR_P is
5673    a MODIFY_EXPR with a lhs of a REAL/IMAGPART_EXPR of a gimple register.
5674 
5675    IMPORTANT NOTE: This promotion is performed by introducing a load of the
5676    other, unmodified part of the complex object just before the total store.
5677    As a consequence, if the object is still uninitialized, an undefined value
5678    will be loaded into a register, which may result in a spurious exception
5679    if the register is floating-point and the value happens to be a signaling
5680    NaN for example.  Then the fully-fledged complex operations lowering pass
5681    followed by a DCE pass are necessary in order to fix things up.  */
5682 
5683 static enum gimplify_status
gimplify_modify_expr_complex_part(tree * expr_p,gimple_seq * pre_p,bool want_value)5684 gimplify_modify_expr_complex_part (tree *expr_p, gimple_seq *pre_p,
5685                                    bool want_value)
5686 {
5687   enum tree_code code, ocode;
5688   tree lhs, rhs, new_rhs, other, realpart, imagpart;
5689 
5690   lhs = TREE_OPERAND (*expr_p, 0);
5691   rhs = TREE_OPERAND (*expr_p, 1);
5692   code = TREE_CODE (lhs);
5693   lhs = TREE_OPERAND (lhs, 0);
5694 
5695   ocode = code == REALPART_EXPR ? IMAGPART_EXPR : REALPART_EXPR;
5696   other = build1 (ocode, TREE_TYPE (rhs), lhs);
5697   TREE_NO_WARNING (other) = 1;
5698   other = get_formal_tmp_var (other, pre_p);
5699 
5700   realpart = code == REALPART_EXPR ? rhs : other;
5701   imagpart = code == REALPART_EXPR ? other : rhs;
5702 
5703   if (TREE_CONSTANT (realpart) && TREE_CONSTANT (imagpart))
5704     new_rhs = build_complex (TREE_TYPE (lhs), realpart, imagpart);
5705   else
5706     new_rhs = build2 (COMPLEX_EXPR, TREE_TYPE (lhs), realpart, imagpart);
5707 
5708   gimplify_seq_add_stmt (pre_p, gimple_build_assign (lhs, new_rhs));
5709   *expr_p = (want_value) ? rhs : NULL_TREE;
5710 
5711   return GS_ALL_DONE;
5712 }
5713 
5714 /* Gimplify the MODIFY_EXPR node pointed to by EXPR_P.
5715 
5716       modify_expr
5717 	      : varname '=' rhs
5718 	      | '*' ID '=' rhs
5719 
5720     PRE_P points to the list where side effects that must happen before
5721 	*EXPR_P should be stored.
5722 
5723     POST_P points to the list where side effects that must happen after
5724 	*EXPR_P should be stored.
5725 
5726     WANT_VALUE is nonzero iff we want to use the value of this expression
5727 	in another expression.  */
5728 
5729 static enum gimplify_status
gimplify_modify_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,bool want_value)5730 gimplify_modify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
5731 		      bool want_value)
5732 {
5733   tree *from_p = &TREE_OPERAND (*expr_p, 1);
5734   tree *to_p = &TREE_OPERAND (*expr_p, 0);
5735   enum gimplify_status ret = GS_UNHANDLED;
5736   gimple *assign;
5737   location_t loc = EXPR_LOCATION (*expr_p);
5738   gimple_stmt_iterator gsi;
5739 
5740   gcc_assert (TREE_CODE (*expr_p) == MODIFY_EXPR
5741 	      || TREE_CODE (*expr_p) == INIT_EXPR);
5742 
5743   /* Trying to simplify a clobber using normal logic doesn't work,
5744      so handle it here.  */
5745   if (TREE_CLOBBER_P (*from_p))
5746     {
5747       ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
5748       if (ret == GS_ERROR)
5749 	return ret;
5750       gcc_assert (!want_value);
5751       if (!VAR_P (*to_p) && TREE_CODE (*to_p) != MEM_REF)
5752 	{
5753 	  tree addr = get_initialized_tmp_var (build_fold_addr_expr (*to_p),
5754 					       pre_p, post_p);
5755 	  *to_p = build_simple_mem_ref_loc (EXPR_LOCATION (*to_p), addr);
5756 	}
5757       gimplify_seq_add_stmt (pre_p, gimple_build_assign (*to_p, *from_p));
5758       *expr_p = NULL;
5759       return GS_ALL_DONE;
5760     }
5761 
5762   /* Insert pointer conversions required by the middle-end that are not
5763      required by the frontend.  This fixes middle-end type checking for
5764      for example gcc.dg/redecl-6.c.  */
5765   if (POINTER_TYPE_P (TREE_TYPE (*to_p)))
5766     {
5767       STRIP_USELESS_TYPE_CONVERSION (*from_p);
5768       if (!useless_type_conversion_p (TREE_TYPE (*to_p), TREE_TYPE (*from_p)))
5769 	*from_p = fold_convert_loc (loc, TREE_TYPE (*to_p), *from_p);
5770     }
5771 
5772   /* See if any simplifications can be done based on what the RHS is.  */
5773   ret = gimplify_modify_expr_rhs (expr_p, from_p, to_p, pre_p, post_p,
5774 				  want_value);
5775   if (ret != GS_UNHANDLED)
5776     return ret;
5777 
5778   /* For zero sized types only gimplify the left hand side and right hand
5779      side as statements and throw away the assignment.  Do this after
5780      gimplify_modify_expr_rhs so we handle TARGET_EXPRs of addressable
5781      types properly.  */
5782   if (zero_sized_type (TREE_TYPE (*from_p))
5783       && !want_value
5784       /* Don't do this for calls that return addressable types, expand_call
5785 	 relies on those having a lhs.  */
5786       && !(TREE_ADDRESSABLE (TREE_TYPE (*from_p))
5787 	   && TREE_CODE (*from_p) == CALL_EXPR))
5788     {
5789       gimplify_stmt (from_p, pre_p);
5790       gimplify_stmt (to_p, pre_p);
5791       *expr_p = NULL_TREE;
5792       return GS_ALL_DONE;
5793     }
5794 
5795   /* If the value being copied is of variable width, compute the length
5796      of the copy into a WITH_SIZE_EXPR.   Note that we need to do this
5797      before gimplifying any of the operands so that we can resolve any
5798      PLACEHOLDER_EXPRs in the size.  Also note that the RTL expander uses
5799      the size of the expression to be copied, not of the destination, so
5800      that is what we must do here.  */
5801   maybe_with_size_expr (from_p);
5802 
5803   /* As a special case, we have to temporarily allow for assignments
5804      with a CALL_EXPR on the RHS.  Since in GIMPLE a function call is
5805      a toplevel statement, when gimplifying the GENERIC expression
5806      MODIFY_EXPR <a, CALL_EXPR <foo>>, we cannot create the tuple
5807      GIMPLE_ASSIGN <a, GIMPLE_CALL <foo>>.
5808 
5809      Instead, we need to create the tuple GIMPLE_CALL <a, foo>.  To
5810      prevent gimplify_expr from trying to create a new temporary for
5811      foo's LHS, we tell it that it should only gimplify until it
5812      reaches the CALL_EXPR.  On return from gimplify_expr, the newly
5813      created GIMPLE_CALL <foo> will be the last statement in *PRE_P
5814      and all we need to do here is set 'a' to be its LHS.  */
5815 
5816   /* Gimplify the RHS first for C++17 and bug 71104.  */
5817   gimple_predicate initial_pred = initial_rhs_predicate_for (*to_p);
5818   ret = gimplify_expr (from_p, pre_p, post_p, initial_pred, fb_rvalue);
5819   if (ret == GS_ERROR)
5820     return ret;
5821 
5822   /* Then gimplify the LHS.  */
5823   /* If we gimplified the RHS to a CALL_EXPR and that call may return
5824      twice we have to make sure to gimplify into non-SSA as otherwise
5825      the abnormal edge added later will make those defs not dominate
5826      their uses.
5827      ???  Technically this applies only to the registers used in the
5828      resulting non-register *TO_P.  */
5829   bool saved_into_ssa = gimplify_ctxp->into_ssa;
5830   if (saved_into_ssa
5831       && TREE_CODE (*from_p) == CALL_EXPR
5832       && call_expr_flags (*from_p) & ECF_RETURNS_TWICE)
5833     gimplify_ctxp->into_ssa = false;
5834   ret = gimplify_expr (to_p, pre_p, post_p, is_gimple_lvalue, fb_lvalue);
5835   gimplify_ctxp->into_ssa = saved_into_ssa;
5836   if (ret == GS_ERROR)
5837     return ret;
5838 
5839   /* Now that the LHS is gimplified, re-gimplify the RHS if our initial
5840      guess for the predicate was wrong.  */
5841   gimple_predicate final_pred = rhs_predicate_for (*to_p);
5842   if (final_pred != initial_pred)
5843     {
5844       ret = gimplify_expr (from_p, pre_p, post_p, final_pred, fb_rvalue);
5845       if (ret == GS_ERROR)
5846 	return ret;
5847     }
5848 
5849   /* In case of va_arg internal fn wrappped in a WITH_SIZE_EXPR, add the type
5850      size as argument to the call.  */
5851   if (TREE_CODE (*from_p) == WITH_SIZE_EXPR)
5852     {
5853       tree call = TREE_OPERAND (*from_p, 0);
5854       tree vlasize = TREE_OPERAND (*from_p, 1);
5855 
5856       if (TREE_CODE (call) == CALL_EXPR
5857 	  && CALL_EXPR_IFN (call) == IFN_VA_ARG)
5858 	{
5859 	  int nargs = call_expr_nargs (call);
5860 	  tree type = TREE_TYPE (call);
5861 	  tree ap = CALL_EXPR_ARG (call, 0);
5862 	  tree tag = CALL_EXPR_ARG (call, 1);
5863 	  tree aptag = CALL_EXPR_ARG (call, 2);
5864 	  tree newcall = build_call_expr_internal_loc (EXPR_LOCATION (call),
5865 						       IFN_VA_ARG, type,
5866 						       nargs + 1, ap, tag,
5867 						       aptag, vlasize);
5868 	  TREE_OPERAND (*from_p, 0) = newcall;
5869 	}
5870     }
5871 
5872   /* Now see if the above changed *from_p to something we handle specially.  */
5873   ret = gimplify_modify_expr_rhs (expr_p, from_p, to_p, pre_p, post_p,
5874 				  want_value);
5875   if (ret != GS_UNHANDLED)
5876     return ret;
5877 
5878   /* If we've got a variable sized assignment between two lvalues (i.e. does
5879      not involve a call), then we can make things a bit more straightforward
5880      by converting the assignment to memcpy or memset.  */
5881   if (TREE_CODE (*from_p) == WITH_SIZE_EXPR)
5882     {
5883       tree from = TREE_OPERAND (*from_p, 0);
5884       tree size = TREE_OPERAND (*from_p, 1);
5885 
5886       if (TREE_CODE (from) == CONSTRUCTOR)
5887 	return gimplify_modify_expr_to_memset (expr_p, size, want_value, pre_p);
5888 
5889       if (is_gimple_addressable (from))
5890 	{
5891 	  *from_p = from;
5892 	  return gimplify_modify_expr_to_memcpy (expr_p, size, want_value,
5893 	      					 pre_p);
5894 	}
5895     }
5896 
5897   /* Transform partial stores to non-addressable complex variables into
5898      total stores.  This allows us to use real instead of virtual operands
5899      for these variables, which improves optimization.  */
5900   if ((TREE_CODE (*to_p) == REALPART_EXPR
5901        || TREE_CODE (*to_p) == IMAGPART_EXPR)
5902       && is_gimple_reg (TREE_OPERAND (*to_p, 0)))
5903     return gimplify_modify_expr_complex_part (expr_p, pre_p, want_value);
5904 
5905   /* Try to alleviate the effects of the gimplification creating artificial
5906      temporaries (see for example is_gimple_reg_rhs) on the debug info, but
5907      make sure not to create DECL_DEBUG_EXPR links across functions.  */
5908   if (!gimplify_ctxp->into_ssa
5909       && VAR_P (*from_p)
5910       && DECL_IGNORED_P (*from_p)
5911       && DECL_P (*to_p)
5912       && !DECL_IGNORED_P (*to_p)
5913       && decl_function_context (*to_p) == current_function_decl
5914       && decl_function_context (*from_p) == current_function_decl)
5915     {
5916       if (!DECL_NAME (*from_p) && DECL_NAME (*to_p))
5917 	DECL_NAME (*from_p)
5918 	  = create_tmp_var_name (IDENTIFIER_POINTER (DECL_NAME (*to_p)));
5919       DECL_HAS_DEBUG_EXPR_P (*from_p) = 1;
5920       SET_DECL_DEBUG_EXPR (*from_p, *to_p);
5921    }
5922 
5923   if (want_value && TREE_THIS_VOLATILE (*to_p))
5924     *from_p = get_initialized_tmp_var (*from_p, pre_p, post_p);
5925 
5926   if (TREE_CODE (*from_p) == CALL_EXPR)
5927     {
5928       /* Since the RHS is a CALL_EXPR, we need to create a GIMPLE_CALL
5929 	 instead of a GIMPLE_ASSIGN.  */
5930       gcall *call_stmt;
5931       if (CALL_EXPR_FN (*from_p) == NULL_TREE)
5932 	{
5933 	  /* Gimplify internal functions created in the FEs.  */
5934 	  int nargs = call_expr_nargs (*from_p), i;
5935 	  enum internal_fn ifn = CALL_EXPR_IFN (*from_p);
5936 	  auto_vec<tree> vargs (nargs);
5937 
5938 	  for (i = 0; i < nargs; i++)
5939 	    {
5940 	      gimplify_arg (&CALL_EXPR_ARG (*from_p, i), pre_p,
5941 			    EXPR_LOCATION (*from_p));
5942 	      vargs.quick_push (CALL_EXPR_ARG (*from_p, i));
5943 	    }
5944 	  call_stmt = gimple_build_call_internal_vec (ifn, vargs);
5945 	  gimple_call_set_nothrow (call_stmt, TREE_NOTHROW (*from_p));
5946 	  gimple_set_location (call_stmt, EXPR_LOCATION (*expr_p));
5947 	}
5948       else
5949 	{
5950 	  tree fnptrtype = TREE_TYPE (CALL_EXPR_FN (*from_p));
5951 	  CALL_EXPR_FN (*from_p) = TREE_OPERAND (CALL_EXPR_FN (*from_p), 0);
5952 	  STRIP_USELESS_TYPE_CONVERSION (CALL_EXPR_FN (*from_p));
5953 	  tree fndecl = get_callee_fndecl (*from_p);
5954 	  if (fndecl
5955 	      && fndecl_built_in_p (fndecl, BUILT_IN_EXPECT)
5956 	      && call_expr_nargs (*from_p) == 3)
5957 	    call_stmt = gimple_build_call_internal (IFN_BUILTIN_EXPECT, 3,
5958 						    CALL_EXPR_ARG (*from_p, 0),
5959 						    CALL_EXPR_ARG (*from_p, 1),
5960 						    CALL_EXPR_ARG (*from_p, 2));
5961 	  else
5962 	    {
5963 	      call_stmt = gimple_build_call_from_tree (*from_p, fnptrtype);
5964 	    }
5965 	}
5966       notice_special_calls (call_stmt);
5967       if (!gimple_call_noreturn_p (call_stmt) || !should_remove_lhs_p (*to_p))
5968 	gimple_call_set_lhs (call_stmt, *to_p);
5969       else if (TREE_CODE (*to_p) == SSA_NAME)
5970 	/* The above is somewhat premature, avoid ICEing later for a
5971 	   SSA name w/o a definition.  We may have uses in the GIMPLE IL.
5972 	   ???  This doesn't make it a default-def.  */
5973 	SSA_NAME_DEF_STMT (*to_p) = gimple_build_nop ();
5974 
5975       assign = call_stmt;
5976     }
5977   else
5978     {
5979       assign = gimple_build_assign (*to_p, *from_p);
5980       gimple_set_location (assign, EXPR_LOCATION (*expr_p));
5981       if (COMPARISON_CLASS_P (*from_p))
5982 	gimple_set_no_warning (assign, TREE_NO_WARNING (*from_p));
5983     }
5984 
5985   if (gimplify_ctxp->into_ssa && is_gimple_reg (*to_p))
5986     {
5987       /* We should have got an SSA name from the start.  */
5988       gcc_assert (TREE_CODE (*to_p) == SSA_NAME
5989 		  || ! gimple_in_ssa_p (cfun));
5990     }
5991 
5992   gimplify_seq_add_stmt (pre_p, assign);
5993   gsi = gsi_last (*pre_p);
5994   maybe_fold_stmt (&gsi);
5995 
5996   if (want_value)
5997     {
5998       *expr_p = TREE_THIS_VOLATILE (*to_p) ? *from_p : unshare_expr (*to_p);
5999       return GS_OK;
6000     }
6001   else
6002     *expr_p = NULL;
6003 
6004   return GS_ALL_DONE;
6005 }
6006 
6007 /* Gimplify a comparison between two variable-sized objects.  Do this
6008    with a call to BUILT_IN_MEMCMP.  */
6009 
6010 static enum gimplify_status
gimplify_variable_sized_compare(tree * expr_p)6011 gimplify_variable_sized_compare (tree *expr_p)
6012 {
6013   location_t loc = EXPR_LOCATION (*expr_p);
6014   tree op0 = TREE_OPERAND (*expr_p, 0);
6015   tree op1 = TREE_OPERAND (*expr_p, 1);
6016   tree t, arg, dest, src, expr;
6017 
6018   arg = TYPE_SIZE_UNIT (TREE_TYPE (op0));
6019   arg = unshare_expr (arg);
6020   arg = SUBSTITUTE_PLACEHOLDER_IN_EXPR (arg, op0);
6021   src = build_fold_addr_expr_loc (loc, op1);
6022   dest = build_fold_addr_expr_loc (loc, op0);
6023   t = builtin_decl_implicit (BUILT_IN_MEMCMP);
6024   t = build_call_expr_loc (loc, t, 3, dest, src, arg);
6025 
6026   expr
6027     = build2 (TREE_CODE (*expr_p), TREE_TYPE (*expr_p), t, integer_zero_node);
6028   SET_EXPR_LOCATION (expr, loc);
6029   *expr_p = expr;
6030 
6031   return GS_OK;
6032 }
6033 
6034 /* Gimplify a comparison between two aggregate objects of integral scalar
6035    mode as a comparison between the bitwise equivalent scalar values.  */
6036 
6037 static enum gimplify_status
gimplify_scalar_mode_aggregate_compare(tree * expr_p)6038 gimplify_scalar_mode_aggregate_compare (tree *expr_p)
6039 {
6040   location_t loc = EXPR_LOCATION (*expr_p);
6041   tree op0 = TREE_OPERAND (*expr_p, 0);
6042   tree op1 = TREE_OPERAND (*expr_p, 1);
6043 
6044   tree type = TREE_TYPE (op0);
6045   tree scalar_type = lang_hooks.types.type_for_mode (TYPE_MODE (type), 1);
6046 
6047   op0 = fold_build1_loc (loc, VIEW_CONVERT_EXPR, scalar_type, op0);
6048   op1 = fold_build1_loc (loc, VIEW_CONVERT_EXPR, scalar_type, op1);
6049 
6050   *expr_p
6051     = fold_build2_loc (loc, TREE_CODE (*expr_p), TREE_TYPE (*expr_p), op0, op1);
6052 
6053   return GS_OK;
6054 }
6055 
6056 /* Gimplify an expression sequence.  This function gimplifies each
6057    expression and rewrites the original expression with the last
6058    expression of the sequence in GIMPLE form.
6059 
6060    PRE_P points to the list where the side effects for all the
6061        expressions in the sequence will be emitted.
6062 
6063    WANT_VALUE is true when the result of the last COMPOUND_EXPR is used.  */
6064 
6065 static enum gimplify_status
gimplify_compound_expr(tree * expr_p,gimple_seq * pre_p,bool want_value)6066 gimplify_compound_expr (tree *expr_p, gimple_seq *pre_p, bool want_value)
6067 {
6068   tree t = *expr_p;
6069 
6070   do
6071     {
6072       tree *sub_p = &TREE_OPERAND (t, 0);
6073 
6074       if (TREE_CODE (*sub_p) == COMPOUND_EXPR)
6075 	gimplify_compound_expr (sub_p, pre_p, false);
6076       else
6077 	gimplify_stmt (sub_p, pre_p);
6078 
6079       t = TREE_OPERAND (t, 1);
6080     }
6081   while (TREE_CODE (t) == COMPOUND_EXPR);
6082 
6083   *expr_p = t;
6084   if (want_value)
6085     return GS_OK;
6086   else
6087     {
6088       gimplify_stmt (expr_p, pre_p);
6089       return GS_ALL_DONE;
6090     }
6091 }
6092 
6093 /* Gimplify a SAVE_EXPR node.  EXPR_P points to the expression to
6094    gimplify.  After gimplification, EXPR_P will point to a new temporary
6095    that holds the original value of the SAVE_EXPR node.
6096 
6097    PRE_P points to the list where side effects that must happen before
6098    *EXPR_P should be stored.  */
6099 
6100 static enum gimplify_status
gimplify_save_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p)6101 gimplify_save_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
6102 {
6103   enum gimplify_status ret = GS_ALL_DONE;
6104   tree val;
6105 
6106   gcc_assert (TREE_CODE (*expr_p) == SAVE_EXPR);
6107   val = TREE_OPERAND (*expr_p, 0);
6108 
6109   /* If the SAVE_EXPR has not been resolved, then evaluate it once.  */
6110   if (!SAVE_EXPR_RESOLVED_P (*expr_p))
6111     {
6112       /* The operand may be a void-valued expression.  It is
6113 	 being executed only for its side-effects.  */
6114       if (TREE_TYPE (val) == void_type_node)
6115 	{
6116 	  ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
6117 			       is_gimple_stmt, fb_none);
6118 	  val = NULL;
6119 	}
6120       else
6121 	/* The temporary may not be an SSA name as later abnormal and EH
6122 	   control flow may invalidate use/def domination.  When in SSA
6123 	   form then assume there are no such issues and SAVE_EXPRs only
6124 	   appear via GENERIC foldings.  */
6125 	val = get_initialized_tmp_var (val, pre_p, post_p,
6126 				       gimple_in_ssa_p (cfun));
6127 
6128       TREE_OPERAND (*expr_p, 0) = val;
6129       SAVE_EXPR_RESOLVED_P (*expr_p) = 1;
6130     }
6131 
6132   *expr_p = val;
6133 
6134   return ret;
6135 }
6136 
6137 /* Rewrite the ADDR_EXPR node pointed to by EXPR_P
6138 
6139       unary_expr
6140 	      : ...
6141 	      | '&' varname
6142 	      ...
6143 
6144     PRE_P points to the list where side effects that must happen before
6145 	*EXPR_P should be stored.
6146 
6147     POST_P points to the list where side effects that must happen after
6148 	*EXPR_P should be stored.  */
6149 
6150 static enum gimplify_status
gimplify_addr_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p)6151 gimplify_addr_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
6152 {
6153   tree expr = *expr_p;
6154   tree op0 = TREE_OPERAND (expr, 0);
6155   enum gimplify_status ret;
6156   location_t loc = EXPR_LOCATION (*expr_p);
6157 
6158   switch (TREE_CODE (op0))
6159     {
6160     case INDIRECT_REF:
6161     do_indirect_ref:
6162       /* Check if we are dealing with an expression of the form '&*ptr'.
6163 	 While the front end folds away '&*ptr' into 'ptr', these
6164 	 expressions may be generated internally by the compiler (e.g.,
6165 	 builtins like __builtin_va_end).  */
6166       /* Caution: the silent array decomposition semantics we allow for
6167 	 ADDR_EXPR means we can't always discard the pair.  */
6168       /* Gimplification of the ADDR_EXPR operand may drop
6169 	 cv-qualification conversions, so make sure we add them if
6170 	 needed.  */
6171       {
6172 	tree op00 = TREE_OPERAND (op0, 0);
6173 	tree t_expr = TREE_TYPE (expr);
6174 	tree t_op00 = TREE_TYPE (op00);
6175 
6176         if (!useless_type_conversion_p (t_expr, t_op00))
6177 	  op00 = fold_convert_loc (loc, TREE_TYPE (expr), op00);
6178         *expr_p = op00;
6179         ret = GS_OK;
6180       }
6181       break;
6182 
6183     case VIEW_CONVERT_EXPR:
6184       /* Take the address of our operand and then convert it to the type of
6185 	 this ADDR_EXPR.
6186 
6187 	 ??? The interactions of VIEW_CONVERT_EXPR and aliasing is not at
6188 	 all clear.  The impact of this transformation is even less clear.  */
6189 
6190       /* If the operand is a useless conversion, look through it.  Doing so
6191 	 guarantees that the ADDR_EXPR and its operand will remain of the
6192 	 same type.  */
6193       if (tree_ssa_useless_type_conversion (TREE_OPERAND (op0, 0)))
6194 	op0 = TREE_OPERAND (op0, 0);
6195 
6196       *expr_p = fold_convert_loc (loc, TREE_TYPE (expr),
6197 				  build_fold_addr_expr_loc (loc,
6198 							TREE_OPERAND (op0, 0)));
6199       ret = GS_OK;
6200       break;
6201 
6202     case MEM_REF:
6203       if (integer_zerop (TREE_OPERAND (op0, 1)))
6204 	goto do_indirect_ref;
6205 
6206       /* fall through */
6207 
6208     default:
6209       /* If we see a call to a declared builtin or see its address
6210 	 being taken (we can unify those cases here) then we can mark
6211 	 the builtin for implicit generation by GCC.  */
6212       if (TREE_CODE (op0) == FUNCTION_DECL
6213 	  && fndecl_built_in_p (op0, BUILT_IN_NORMAL)
6214 	  && builtin_decl_declared_p (DECL_FUNCTION_CODE (op0)))
6215 	set_builtin_decl_implicit_p (DECL_FUNCTION_CODE (op0), true);
6216 
6217       /* We use fb_either here because the C frontend sometimes takes
6218 	 the address of a call that returns a struct; see
6219 	 gcc.dg/c99-array-lval-1.c.  The gimplifier will correctly make
6220 	 the implied temporary explicit.  */
6221 
6222       /* Make the operand addressable.  */
6223       ret = gimplify_expr (&TREE_OPERAND (expr, 0), pre_p, post_p,
6224 			   is_gimple_addressable, fb_either);
6225       if (ret == GS_ERROR)
6226 	break;
6227 
6228       /* Then mark it.  Beware that it may not be possible to do so directly
6229 	 if a temporary has been created by the gimplification.  */
6230       prepare_gimple_addressable (&TREE_OPERAND (expr, 0), pre_p);
6231 
6232       op0 = TREE_OPERAND (expr, 0);
6233 
6234       /* For various reasons, the gimplification of the expression
6235 	 may have made a new INDIRECT_REF.  */
6236       if (TREE_CODE (op0) == INDIRECT_REF
6237 	  || (TREE_CODE (op0) == MEM_REF
6238 	      && integer_zerop (TREE_OPERAND (op0, 1))))
6239 	goto do_indirect_ref;
6240 
6241       mark_addressable (TREE_OPERAND (expr, 0));
6242 
6243       /* The FEs may end up building ADDR_EXPRs early on a decl with
6244 	 an incomplete type.  Re-build ADDR_EXPRs in canonical form
6245 	 here.  */
6246       if (!types_compatible_p (TREE_TYPE (op0), TREE_TYPE (TREE_TYPE (expr))))
6247 	*expr_p = build_fold_addr_expr (op0);
6248 
6249       /* Make sure TREE_CONSTANT and TREE_SIDE_EFFECTS are set properly.  */
6250       recompute_tree_invariant_for_addr_expr (*expr_p);
6251 
6252       /* If we re-built the ADDR_EXPR add a conversion to the original type
6253          if required.  */
6254       if (!useless_type_conversion_p (TREE_TYPE (expr), TREE_TYPE (*expr_p)))
6255 	*expr_p = fold_convert (TREE_TYPE (expr), *expr_p);
6256 
6257       break;
6258     }
6259 
6260   return ret;
6261 }
6262 
6263 /* Gimplify the operands of an ASM_EXPR.  Input operands should be a gimple
6264    value; output operands should be a gimple lvalue.  */
6265 
6266 static enum gimplify_status
gimplify_asm_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p)6267 gimplify_asm_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
6268 {
6269   tree expr;
6270   int noutputs;
6271   const char **oconstraints;
6272   int i;
6273   tree link;
6274   const char *constraint;
6275   bool allows_mem, allows_reg, is_inout;
6276   enum gimplify_status ret, tret;
6277   gasm *stmt;
6278   vec<tree, va_gc> *inputs;
6279   vec<tree, va_gc> *outputs;
6280   vec<tree, va_gc> *clobbers;
6281   vec<tree, va_gc> *labels;
6282   tree link_next;
6283 
6284   expr = *expr_p;
6285   noutputs = list_length (ASM_OUTPUTS (expr));
6286   oconstraints = (const char **) alloca ((noutputs) * sizeof (const char *));
6287 
6288   inputs = NULL;
6289   outputs = NULL;
6290   clobbers = NULL;
6291   labels = NULL;
6292 
6293   ret = GS_ALL_DONE;
6294   link_next = NULL_TREE;
6295   for (i = 0, link = ASM_OUTPUTS (expr); link; ++i, link = link_next)
6296     {
6297       bool ok;
6298       size_t constraint_len;
6299 
6300       link_next = TREE_CHAIN (link);
6301 
6302       oconstraints[i]
6303 	= constraint
6304 	= TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
6305       constraint_len = strlen (constraint);
6306       if (constraint_len == 0)
6307         continue;
6308 
6309       ok = parse_output_constraint (&constraint, i, 0, 0,
6310 				    &allows_mem, &allows_reg, &is_inout);
6311       if (!ok)
6312 	{
6313 	  ret = GS_ERROR;
6314 	  is_inout = false;
6315 	}
6316 
6317       /* If we can't make copies, we can only accept memory.
6318 	 Similarly for VLAs.  */
6319       tree outtype = TREE_TYPE (TREE_VALUE (link));
6320       if (outtype != error_mark_node
6321 	  && (TREE_ADDRESSABLE (outtype)
6322 	      || !COMPLETE_TYPE_P (outtype)
6323 	      || !tree_fits_poly_uint64_p (TYPE_SIZE_UNIT (outtype))))
6324 	{
6325 	  if (allows_mem)
6326 	    allows_reg = 0;
6327 	  else
6328 	    {
6329 	      error ("impossible constraint in %<asm%>");
6330 	      error ("non-memory output %d must stay in memory", i);
6331 	      return GS_ERROR;
6332 	    }
6333 	}
6334 
6335       if (!allows_reg && allows_mem)
6336 	mark_addressable (TREE_VALUE (link));
6337 
6338       tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
6339 			    is_inout ? is_gimple_min_lval : is_gimple_lvalue,
6340 			    fb_lvalue | fb_mayfail);
6341       if (tret == GS_ERROR)
6342 	{
6343 	  error ("invalid lvalue in %<asm%> output %d", i);
6344 	  ret = tret;
6345 	}
6346 
6347       /* If the constraint does not allow memory make sure we gimplify
6348          it to a register if it is not already but its base is.  This
6349 	 happens for complex and vector components.  */
6350       if (!allows_mem)
6351 	{
6352 	  tree op = TREE_VALUE (link);
6353 	  if (! is_gimple_val (op)
6354 	      && is_gimple_reg_type (TREE_TYPE (op))
6355 	      && is_gimple_reg (get_base_address (op)))
6356 	    {
6357 	      tree tem = create_tmp_reg (TREE_TYPE (op));
6358 	      tree ass;
6359 	      if (is_inout)
6360 		{
6361 		  ass = build2 (MODIFY_EXPR, TREE_TYPE (tem),
6362 				tem, unshare_expr (op));
6363 		  gimplify_and_add (ass, pre_p);
6364 		}
6365 	      ass = build2 (MODIFY_EXPR, TREE_TYPE (tem), op, tem);
6366 	      gimplify_and_add (ass, post_p);
6367 
6368 	      TREE_VALUE (link) = tem;
6369 	      tret = GS_OK;
6370 	    }
6371 	}
6372 
6373       vec_safe_push (outputs, link);
6374       TREE_CHAIN (link) = NULL_TREE;
6375 
6376       if (is_inout)
6377 	{
6378 	  /* An input/output operand.  To give the optimizers more
6379 	     flexibility, split it into separate input and output
6380  	     operands.  */
6381 	  tree input;
6382 	  /* Buffer big enough to format a 32-bit UINT_MAX into.  */
6383 	  char buf[11];
6384 
6385 	  /* Turn the in/out constraint into an output constraint.  */
6386 	  char *p = xstrdup (constraint);
6387 	  p[0] = '=';
6388 	  TREE_VALUE (TREE_PURPOSE (link)) = build_string (constraint_len, p);
6389 
6390 	  /* And add a matching input constraint.  */
6391 	  if (allows_reg)
6392 	    {
6393 	      sprintf (buf, "%u", i);
6394 
6395 	      /* If there are multiple alternatives in the constraint,
6396 		 handle each of them individually.  Those that allow register
6397 		 will be replaced with operand number, the others will stay
6398 		 unchanged.  */
6399 	      if (strchr (p, ',') != NULL)
6400 		{
6401 		  size_t len = 0, buflen = strlen (buf);
6402 		  char *beg, *end, *str, *dst;
6403 
6404 		  for (beg = p + 1;;)
6405 		    {
6406 		      end = strchr (beg, ',');
6407 		      if (end == NULL)
6408 			end = strchr (beg, '\0');
6409 		      if ((size_t) (end - beg) < buflen)
6410 			len += buflen + 1;
6411 		      else
6412 			len += end - beg + 1;
6413 		      if (*end)
6414 			beg = end + 1;
6415 		      else
6416 			break;
6417 		    }
6418 
6419 		  str = (char *) alloca (len);
6420 		  for (beg = p + 1, dst = str;;)
6421 		    {
6422 		      const char *tem;
6423 		      bool mem_p, reg_p, inout_p;
6424 
6425 		      end = strchr (beg, ',');
6426 		      if (end)
6427 			*end = '\0';
6428 		      beg[-1] = '=';
6429 		      tem = beg - 1;
6430 		      parse_output_constraint (&tem, i, 0, 0,
6431 					       &mem_p, &reg_p, &inout_p);
6432 		      if (dst != str)
6433 			*dst++ = ',';
6434 		      if (reg_p)
6435 			{
6436 			  memcpy (dst, buf, buflen);
6437 			  dst += buflen;
6438 			}
6439 		      else
6440 			{
6441 			  if (end)
6442 			    len = end - beg;
6443 			  else
6444 			    len = strlen (beg);
6445 			  memcpy (dst, beg, len);
6446 			  dst += len;
6447 			}
6448 		      if (end)
6449 			beg = end + 1;
6450 		      else
6451 			break;
6452 		    }
6453 		  *dst = '\0';
6454 		  input = build_string (dst - str, str);
6455 		}
6456 	      else
6457 		input = build_string (strlen (buf), buf);
6458 	    }
6459 	  else
6460 	    input = build_string (constraint_len - 1, constraint + 1);
6461 
6462 	  free (p);
6463 
6464 	  input = build_tree_list (build_tree_list (NULL_TREE, input),
6465 				   unshare_expr (TREE_VALUE (link)));
6466 	  ASM_INPUTS (expr) = chainon (ASM_INPUTS (expr), input);
6467 	}
6468     }
6469 
6470   link_next = NULL_TREE;
6471   for (link = ASM_INPUTS (expr); link; ++i, link = link_next)
6472     {
6473       link_next = TREE_CHAIN (link);
6474       constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
6475       parse_input_constraint (&constraint, 0, 0, noutputs, 0,
6476 			      oconstraints, &allows_mem, &allows_reg);
6477 
6478       /* If we can't make copies, we can only accept memory.  */
6479       tree intype = TREE_TYPE (TREE_VALUE (link));
6480       if (intype != error_mark_node
6481 	  && (TREE_ADDRESSABLE (intype)
6482 	      || !COMPLETE_TYPE_P (intype)
6483 	      || !tree_fits_poly_uint64_p (TYPE_SIZE_UNIT (intype))))
6484 	{
6485 	  if (allows_mem)
6486 	    allows_reg = 0;
6487 	  else
6488 	    {
6489 	      error ("impossible constraint in %<asm%>");
6490 	      error ("non-memory input %d must stay in memory", i);
6491 	      return GS_ERROR;
6492 	    }
6493 	}
6494 
6495       /* If the operand is a memory input, it should be an lvalue.  */
6496       if (!allows_reg && allows_mem)
6497 	{
6498 	  tree inputv = TREE_VALUE (link);
6499 	  STRIP_NOPS (inputv);
6500 	  if (TREE_CODE (inputv) == PREDECREMENT_EXPR
6501 	      || TREE_CODE (inputv) == PREINCREMENT_EXPR
6502 	      || TREE_CODE (inputv) == POSTDECREMENT_EXPR
6503 	      || TREE_CODE (inputv) == POSTINCREMENT_EXPR
6504 	      || TREE_CODE (inputv) == MODIFY_EXPR)
6505 	    TREE_VALUE (link) = error_mark_node;
6506 	  tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
6507 				is_gimple_lvalue, fb_lvalue | fb_mayfail);
6508 	  if (tret != GS_ERROR)
6509 	    {
6510 	      /* Unlike output operands, memory inputs are not guaranteed
6511 		 to be lvalues by the FE, and while the expressions are
6512 		 marked addressable there, if it is e.g. a statement
6513 		 expression, temporaries in it might not end up being
6514 		 addressable.  They might be already used in the IL and thus
6515 		 it is too late to make them addressable now though.  */
6516 	      tree x = TREE_VALUE (link);
6517 	      while (handled_component_p (x))
6518 		x = TREE_OPERAND (x, 0);
6519 	      if (TREE_CODE (x) == MEM_REF
6520 		  && TREE_CODE (TREE_OPERAND (x, 0)) == ADDR_EXPR)
6521 		x = TREE_OPERAND (TREE_OPERAND (x, 0), 0);
6522 	      if ((VAR_P (x)
6523 		   || TREE_CODE (x) == PARM_DECL
6524 		   || TREE_CODE (x) == RESULT_DECL)
6525 		  && !TREE_ADDRESSABLE (x)
6526 		  && is_gimple_reg (x))
6527 		{
6528 		  warning_at (EXPR_LOC_OR_LOC (TREE_VALUE (link),
6529 					       input_location), 0,
6530 			      "memory input %d is not directly addressable",
6531 			      i);
6532 		  prepare_gimple_addressable (&TREE_VALUE (link), pre_p);
6533 		}
6534 	    }
6535 	  mark_addressable (TREE_VALUE (link));
6536 	  if (tret == GS_ERROR)
6537 	    {
6538 	      error_at (EXPR_LOC_OR_LOC (TREE_VALUE (link), input_location),
6539 			"memory input %d is not directly addressable", i);
6540 	      ret = tret;
6541 	    }
6542 	}
6543       else
6544 	{
6545 	  tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
6546 				is_gimple_asm_val, fb_rvalue);
6547 	  if (tret == GS_ERROR)
6548 	    ret = tret;
6549 	}
6550 
6551       TREE_CHAIN (link) = NULL_TREE;
6552       vec_safe_push (inputs, link);
6553     }
6554 
6555   link_next = NULL_TREE;
6556   for (link = ASM_CLOBBERS (expr); link; ++i, link = link_next)
6557     {
6558       link_next = TREE_CHAIN (link);
6559       TREE_CHAIN (link) = NULL_TREE;
6560       vec_safe_push (clobbers, link);
6561     }
6562 
6563   link_next = NULL_TREE;
6564   for (link = ASM_LABELS (expr); link; ++i, link = link_next)
6565     {
6566       link_next = TREE_CHAIN (link);
6567       TREE_CHAIN (link) = NULL_TREE;
6568       vec_safe_push (labels, link);
6569     }
6570 
6571   /* Do not add ASMs with errors to the gimple IL stream.  */
6572   if (ret != GS_ERROR)
6573     {
6574       stmt = gimple_build_asm_vec (TREE_STRING_POINTER (ASM_STRING (expr)),
6575 				   inputs, outputs, clobbers, labels);
6576 
6577       gimple_asm_set_volatile (stmt, ASM_VOLATILE_P (expr) || noutputs == 0);
6578       gimple_asm_set_input (stmt, ASM_INPUT_P (expr));
6579       gimple_asm_set_inline (stmt, ASM_INLINE_P (expr));
6580 
6581       gimplify_seq_add_stmt (pre_p, stmt);
6582     }
6583 
6584   return ret;
6585 }
6586 
6587 /* Gimplify a CLEANUP_POINT_EXPR.  Currently this works by adding
6588    GIMPLE_WITH_CLEANUP_EXPRs to the prequeue as we encounter cleanups while
6589    gimplifying the body, and converting them to TRY_FINALLY_EXPRs when we
6590    return to this function.
6591 
6592    FIXME should we complexify the prequeue handling instead?  Or use flags
6593    for all the cleanups and let the optimizer tighten them up?  The current
6594    code seems pretty fragile; it will break on a cleanup within any
6595    non-conditional nesting.  But any such nesting would be broken, anyway;
6596    we can't write a TRY_FINALLY_EXPR that starts inside a nesting construct
6597    and continues out of it.  We can do that at the RTL level, though, so
6598    having an optimizer to tighten up try/finally regions would be a Good
6599    Thing.  */
6600 
6601 static enum gimplify_status
gimplify_cleanup_point_expr(tree * expr_p,gimple_seq * pre_p)6602 gimplify_cleanup_point_expr (tree *expr_p, gimple_seq *pre_p)
6603 {
6604   gimple_stmt_iterator iter;
6605   gimple_seq body_sequence = NULL;
6606 
6607   tree temp = voidify_wrapper_expr (*expr_p, NULL);
6608 
6609   /* We only care about the number of conditions between the innermost
6610      CLEANUP_POINT_EXPR and the cleanup.  So save and reset the count and
6611      any cleanups collected outside the CLEANUP_POINT_EXPR.  */
6612   int old_conds = gimplify_ctxp->conditions;
6613   gimple_seq old_cleanups = gimplify_ctxp->conditional_cleanups;
6614   bool old_in_cleanup_point_expr = gimplify_ctxp->in_cleanup_point_expr;
6615   gimplify_ctxp->conditions = 0;
6616   gimplify_ctxp->conditional_cleanups = NULL;
6617   gimplify_ctxp->in_cleanup_point_expr = true;
6618 
6619   gimplify_stmt (&TREE_OPERAND (*expr_p, 0), &body_sequence);
6620 
6621   gimplify_ctxp->conditions = old_conds;
6622   gimplify_ctxp->conditional_cleanups = old_cleanups;
6623   gimplify_ctxp->in_cleanup_point_expr = old_in_cleanup_point_expr;
6624 
6625   for (iter = gsi_start (body_sequence); !gsi_end_p (iter); )
6626     {
6627       gimple *wce = gsi_stmt (iter);
6628 
6629       if (gimple_code (wce) == GIMPLE_WITH_CLEANUP_EXPR)
6630 	{
6631 	  if (gsi_one_before_end_p (iter))
6632 	    {
6633               /* Note that gsi_insert_seq_before and gsi_remove do not
6634                  scan operands, unlike some other sequence mutators.  */
6635 	      if (!gimple_wce_cleanup_eh_only (wce))
6636 		gsi_insert_seq_before_without_update (&iter,
6637 						      gimple_wce_cleanup (wce),
6638 						      GSI_SAME_STMT);
6639 	      gsi_remove (&iter, true);
6640 	      break;
6641 	    }
6642 	  else
6643 	    {
6644 	      gtry *gtry;
6645 	      gimple_seq seq;
6646 	      enum gimple_try_flags kind;
6647 
6648 	      if (gimple_wce_cleanup_eh_only (wce))
6649 		kind = GIMPLE_TRY_CATCH;
6650 	      else
6651 		kind = GIMPLE_TRY_FINALLY;
6652 	      seq = gsi_split_seq_after (iter);
6653 
6654 	      gtry = gimple_build_try (seq, gimple_wce_cleanup (wce), kind);
6655               /* Do not use gsi_replace here, as it may scan operands.
6656                  We want to do a simple structural modification only.  */
6657 	      gsi_set_stmt (&iter, gtry);
6658 	      iter = gsi_start (gtry->eval);
6659 	    }
6660 	}
6661       else
6662 	gsi_next (&iter);
6663     }
6664 
6665   gimplify_seq_add_seq (pre_p, body_sequence);
6666   if (temp)
6667     {
6668       *expr_p = temp;
6669       return GS_OK;
6670     }
6671   else
6672     {
6673       *expr_p = NULL;
6674       return GS_ALL_DONE;
6675     }
6676 }
6677 
6678 /* Insert a cleanup marker for gimplify_cleanup_point_expr.  CLEANUP
6679    is the cleanup action required.  EH_ONLY is true if the cleanup should
6680    only be executed if an exception is thrown, not on normal exit.
6681    If FORCE_UNCOND is true perform the cleanup unconditionally;  this is
6682    only valid for clobbers.  */
6683 
6684 static void
6685 gimple_push_cleanup (tree var, tree cleanup, bool eh_only, gimple_seq *pre_p,
6686 		     bool force_uncond = false)
6687 {
6688   gimple *wce;
6689   gimple_seq cleanup_stmts = NULL;
6690 
6691   /* Errors can result in improperly nested cleanups.  Which results in
6692      confusion when trying to resolve the GIMPLE_WITH_CLEANUP_EXPR.  */
6693   if (seen_error ())
6694     return;
6695 
6696   if (gimple_conditional_context ())
6697     {
6698       /* If we're in a conditional context, this is more complex.  We only
6699 	 want to run the cleanup if we actually ran the initialization that
6700 	 necessitates it, but we want to run it after the end of the
6701 	 conditional context.  So we wrap the try/finally around the
6702 	 condition and use a flag to determine whether or not to actually
6703 	 run the destructor.  Thus
6704 
6705 	   test ? f(A()) : 0
6706 
6707 	 becomes (approximately)
6708 
6709 	   flag = 0;
6710 	   try {
6711 	     if (test) { A::A(temp); flag = 1; val = f(temp); }
6712 	     else { val = 0; }
6713 	   } finally {
6714 	     if (flag) A::~A(temp);
6715 	   }
6716 	   val
6717       */
6718       if (force_uncond)
6719 	{
6720 	  gimplify_stmt (&cleanup, &cleanup_stmts);
6721 	  wce = gimple_build_wce (cleanup_stmts);
6722 	  gimplify_seq_add_stmt (&gimplify_ctxp->conditional_cleanups, wce);
6723 	}
6724       else
6725 	{
6726 	  tree flag = create_tmp_var (boolean_type_node, "cleanup");
6727 	  gassign *ffalse = gimple_build_assign (flag, boolean_false_node);
6728 	  gassign *ftrue = gimple_build_assign (flag, boolean_true_node);
6729 
6730 	  cleanup = build3 (COND_EXPR, void_type_node, flag, cleanup, NULL);
6731 	  gimplify_stmt (&cleanup, &cleanup_stmts);
6732 	  wce = gimple_build_wce (cleanup_stmts);
6733 
6734 	  gimplify_seq_add_stmt (&gimplify_ctxp->conditional_cleanups, ffalse);
6735 	  gimplify_seq_add_stmt (&gimplify_ctxp->conditional_cleanups, wce);
6736 	  gimplify_seq_add_stmt (pre_p, ftrue);
6737 
6738 	  /* Because of this manipulation, and the EH edges that jump
6739 	     threading cannot redirect, the temporary (VAR) will appear
6740 	     to be used uninitialized.  Don't warn.  */
6741 	  TREE_NO_WARNING (var) = 1;
6742 	}
6743     }
6744   else
6745     {
6746       gimplify_stmt (&cleanup, &cleanup_stmts);
6747       wce = gimple_build_wce (cleanup_stmts);
6748       gimple_wce_set_cleanup_eh_only (wce, eh_only);
6749       gimplify_seq_add_stmt (pre_p, wce);
6750     }
6751 }
6752 
6753 /* Gimplify a TARGET_EXPR which doesn't appear on the rhs of an INIT_EXPR.  */
6754 
6755 static enum gimplify_status
gimplify_target_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p)6756 gimplify_target_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
6757 {
6758   tree targ = *expr_p;
6759   tree temp = TARGET_EXPR_SLOT (targ);
6760   tree init = TARGET_EXPR_INITIAL (targ);
6761   enum gimplify_status ret;
6762 
6763   bool unpoison_empty_seq = false;
6764   gimple_stmt_iterator unpoison_it;
6765 
6766   if (init)
6767     {
6768       tree cleanup = NULL_TREE;
6769 
6770       /* TARGET_EXPR temps aren't part of the enclosing block, so add it
6771 	 to the temps list.  Handle also variable length TARGET_EXPRs.  */
6772       if (!poly_int_tree_p (DECL_SIZE (temp)))
6773 	{
6774 	  if (!TYPE_SIZES_GIMPLIFIED (TREE_TYPE (temp)))
6775 	    gimplify_type_sizes (TREE_TYPE (temp), pre_p);
6776 	  gimplify_vla_decl (temp, pre_p);
6777 	}
6778       else
6779 	{
6780 	  /* Save location where we need to place unpoisoning.  It's possible
6781 	     that a variable will be converted to needs_to_live_in_memory.  */
6782 	  unpoison_it = gsi_last (*pre_p);
6783 	  unpoison_empty_seq = gsi_end_p (unpoison_it);
6784 
6785 	  gimple_add_tmp_var (temp);
6786 	}
6787 
6788       /* If TARGET_EXPR_INITIAL is void, then the mere evaluation of the
6789 	 expression is supposed to initialize the slot.  */
6790       if (VOID_TYPE_P (TREE_TYPE (init)))
6791 	ret = gimplify_expr (&init, pre_p, post_p, is_gimple_stmt, fb_none);
6792       else
6793 	{
6794 	  tree init_expr = build2 (INIT_EXPR, void_type_node, temp, init);
6795 	  init = init_expr;
6796 	  ret = gimplify_expr (&init, pre_p, post_p, is_gimple_stmt, fb_none);
6797 	  init = NULL;
6798 	  ggc_free (init_expr);
6799 	}
6800       if (ret == GS_ERROR)
6801 	{
6802 	  /* PR c++/28266 Make sure this is expanded only once. */
6803 	  TARGET_EXPR_INITIAL (targ) = NULL_TREE;
6804 	  return GS_ERROR;
6805 	}
6806       if (init)
6807 	gimplify_and_add (init, pre_p);
6808 
6809       /* If needed, push the cleanup for the temp.  */
6810       if (TARGET_EXPR_CLEANUP (targ))
6811 	{
6812 	  if (CLEANUP_EH_ONLY (targ))
6813 	    gimple_push_cleanup (temp, TARGET_EXPR_CLEANUP (targ),
6814 				 CLEANUP_EH_ONLY (targ), pre_p);
6815 	  else
6816 	    cleanup = TARGET_EXPR_CLEANUP (targ);
6817 	}
6818 
6819       /* Add a clobber for the temporary going out of scope, like
6820 	 gimplify_bind_expr.  */
6821       if (gimplify_ctxp->in_cleanup_point_expr
6822 	  && needs_to_live_in_memory (temp))
6823 	{
6824 	  if (flag_stack_reuse == SR_ALL)
6825 	    {
6826 	      tree clobber = build_clobber (TREE_TYPE (temp));
6827 	      clobber = build2 (MODIFY_EXPR, TREE_TYPE (temp), temp, clobber);
6828 	      gimple_push_cleanup (temp, clobber, false, pre_p, true);
6829 	    }
6830 	  if (asan_poisoned_variables
6831 	      && DECL_ALIGN (temp) <= MAX_SUPPORTED_STACK_ALIGNMENT
6832 	      && !TREE_STATIC (temp)
6833 	      && dbg_cnt (asan_use_after_scope)
6834 	      && !gimplify_omp_ctxp)
6835 	    {
6836 	      tree asan_cleanup = build_asan_poison_call_expr (temp);
6837 	      if (asan_cleanup)
6838 		{
6839 		  if (unpoison_empty_seq)
6840 		    unpoison_it = gsi_start (*pre_p);
6841 
6842 		  asan_poison_variable (temp, false, &unpoison_it,
6843 					unpoison_empty_seq);
6844 		  gimple_push_cleanup (temp, asan_cleanup, false, pre_p);
6845 		}
6846 	    }
6847 	}
6848       if (cleanup)
6849 	gimple_push_cleanup (temp, cleanup, false, pre_p);
6850 
6851       /* Only expand this once.  */
6852       TREE_OPERAND (targ, 3) = init;
6853       TARGET_EXPR_INITIAL (targ) = NULL_TREE;
6854     }
6855   else
6856     /* We should have expanded this before.  */
6857     gcc_assert (DECL_SEEN_IN_BIND_EXPR_P (temp));
6858 
6859   *expr_p = temp;
6860   return GS_OK;
6861 }
6862 
6863 /* Gimplification of expression trees.  */
6864 
6865 /* Gimplify an expression which appears at statement context.  The
6866    corresponding GIMPLE statements are added to *SEQ_P.  If *SEQ_P is
6867    NULL, a new sequence is allocated.
6868 
6869    Return true if we actually added a statement to the queue.  */
6870 
6871 bool
gimplify_stmt(tree * stmt_p,gimple_seq * seq_p)6872 gimplify_stmt (tree *stmt_p, gimple_seq *seq_p)
6873 {
6874   gimple_seq_node last;
6875 
6876   last = gimple_seq_last (*seq_p);
6877   gimplify_expr (stmt_p, seq_p, NULL, is_gimple_stmt, fb_none);
6878   return last != gimple_seq_last (*seq_p);
6879 }
6880 
6881 /* Add FIRSTPRIVATE entries for DECL in the OpenMP the surrounding parallels
6882    to CTX.  If entries already exist, force them to be some flavor of private.
6883    If there is no enclosing parallel, do nothing.  */
6884 
6885 void
omp_firstprivatize_variable(struct gimplify_omp_ctx * ctx,tree decl)6886 omp_firstprivatize_variable (struct gimplify_omp_ctx *ctx, tree decl)
6887 {
6888   splay_tree_node n;
6889 
6890   if (decl == NULL || !DECL_P (decl) || ctx->region_type == ORT_NONE)
6891     return;
6892 
6893   do
6894     {
6895       n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
6896       if (n != NULL)
6897 	{
6898 	  if (n->value & GOVD_SHARED)
6899 	    n->value = GOVD_FIRSTPRIVATE | (n->value & GOVD_SEEN);
6900 	  else if (n->value & GOVD_MAP)
6901 	    n->value |= GOVD_MAP_TO_ONLY;
6902 	  else
6903 	    return;
6904 	}
6905       else if ((ctx->region_type & ORT_TARGET) != 0)
6906 	{
6907 	  if (ctx->defaultmap[GDMK_SCALAR] & GOVD_FIRSTPRIVATE)
6908 	    omp_add_variable (ctx, decl, GOVD_FIRSTPRIVATE);
6909 	  else
6910 	    omp_add_variable (ctx, decl, GOVD_MAP | GOVD_MAP_TO_ONLY);
6911 	}
6912       else if (ctx->region_type != ORT_WORKSHARE
6913 	       && ctx->region_type != ORT_TASKGROUP
6914 	       && ctx->region_type != ORT_SIMD
6915 	       && ctx->region_type != ORT_ACC
6916 	       && !(ctx->region_type & ORT_TARGET_DATA))
6917 	omp_add_variable (ctx, decl, GOVD_FIRSTPRIVATE);
6918 
6919       ctx = ctx->outer_context;
6920     }
6921   while (ctx);
6922 }
6923 
6924 /* Similarly for each of the type sizes of TYPE.  */
6925 
6926 static void
omp_firstprivatize_type_sizes(struct gimplify_omp_ctx * ctx,tree type)6927 omp_firstprivatize_type_sizes (struct gimplify_omp_ctx *ctx, tree type)
6928 {
6929   if (type == NULL || type == error_mark_node)
6930     return;
6931   type = TYPE_MAIN_VARIANT (type);
6932 
6933   if (ctx->privatized_types->add (type))
6934     return;
6935 
6936   switch (TREE_CODE (type))
6937     {
6938     case INTEGER_TYPE:
6939     case ENUMERAL_TYPE:
6940     case BOOLEAN_TYPE:
6941     case REAL_TYPE:
6942     case FIXED_POINT_TYPE:
6943       omp_firstprivatize_variable (ctx, TYPE_MIN_VALUE (type));
6944       omp_firstprivatize_variable (ctx, TYPE_MAX_VALUE (type));
6945       break;
6946 
6947     case ARRAY_TYPE:
6948       omp_firstprivatize_type_sizes (ctx, TREE_TYPE (type));
6949       omp_firstprivatize_type_sizes (ctx, TYPE_DOMAIN (type));
6950       break;
6951 
6952     case RECORD_TYPE:
6953     case UNION_TYPE:
6954     case QUAL_UNION_TYPE:
6955       {
6956 	tree field;
6957 	for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
6958 	  if (TREE_CODE (field) == FIELD_DECL)
6959 	    {
6960 	      omp_firstprivatize_variable (ctx, DECL_FIELD_OFFSET (field));
6961 	      omp_firstprivatize_type_sizes (ctx, TREE_TYPE (field));
6962 	    }
6963       }
6964       break;
6965 
6966     case POINTER_TYPE:
6967     case REFERENCE_TYPE:
6968       omp_firstprivatize_type_sizes (ctx, TREE_TYPE (type));
6969       break;
6970 
6971     default:
6972       break;
6973     }
6974 
6975   omp_firstprivatize_variable (ctx, TYPE_SIZE (type));
6976   omp_firstprivatize_variable (ctx, TYPE_SIZE_UNIT (type));
6977   lang_hooks.types.omp_firstprivatize_type_sizes (ctx, type);
6978 }
6979 
6980 /* Add an entry for DECL in the OMP context CTX with FLAGS.  */
6981 
6982 static void
omp_add_variable(struct gimplify_omp_ctx * ctx,tree decl,unsigned int flags)6983 omp_add_variable (struct gimplify_omp_ctx *ctx, tree decl, unsigned int flags)
6984 {
6985   splay_tree_node n;
6986   unsigned int nflags;
6987   tree t;
6988 
6989   if (error_operand_p (decl) || ctx->region_type == ORT_NONE)
6990     return;
6991 
6992   /* Never elide decls whose type has TREE_ADDRESSABLE set.  This means
6993      there are constructors involved somewhere.  Exception is a shared clause,
6994      there is nothing privatized in that case.  */
6995   if ((flags & GOVD_SHARED) == 0
6996       && (TREE_ADDRESSABLE (TREE_TYPE (decl))
6997 	  || TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl))))
6998     flags |= GOVD_SEEN;
6999 
7000   n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
7001   if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
7002     {
7003       /* We shouldn't be re-adding the decl with the same data
7004 	 sharing class.  */
7005       gcc_assert ((n->value & GOVD_DATA_SHARE_CLASS & flags) == 0);
7006       nflags = n->value | flags;
7007       /* The only combination of data sharing classes we should see is
7008 	 FIRSTPRIVATE and LASTPRIVATE.  However, OpenACC permits
7009 	 reduction variables to be used in data sharing clauses.  */
7010       gcc_assert ((ctx->region_type & ORT_ACC) != 0
7011 		  || ((nflags & GOVD_DATA_SHARE_CLASS)
7012 		      == (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE))
7013 		  || (flags & GOVD_DATA_SHARE_CLASS) == 0);
7014       n->value = nflags;
7015       return;
7016     }
7017 
7018   /* When adding a variable-sized variable, we have to handle all sorts
7019      of additional bits of data: the pointer replacement variable, and
7020      the parameters of the type.  */
7021   if (DECL_SIZE (decl) && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
7022     {
7023       /* Add the pointer replacement variable as PRIVATE if the variable
7024 	 replacement is private, else FIRSTPRIVATE since we'll need the
7025 	 address of the original variable either for SHARED, or for the
7026 	 copy into or out of the context.  */
7027       if (!(flags & GOVD_LOCAL) && ctx->region_type != ORT_TASKGROUP)
7028 	{
7029 	  if (flags & GOVD_MAP)
7030 	    nflags = GOVD_MAP | GOVD_MAP_TO_ONLY | GOVD_EXPLICIT;
7031 	  else if (flags & GOVD_PRIVATE)
7032 	    nflags = GOVD_PRIVATE;
7033 	  else if (((ctx->region_type & (ORT_TARGET | ORT_TARGET_DATA)) != 0
7034 		    && (flags & GOVD_FIRSTPRIVATE))
7035 		   || (ctx->region_type == ORT_TARGET_DATA
7036 		       && (flags & GOVD_DATA_SHARE_CLASS) == 0))
7037 	    nflags = GOVD_PRIVATE | GOVD_EXPLICIT;
7038 	  else
7039 	    nflags = GOVD_FIRSTPRIVATE;
7040 	  nflags |= flags & GOVD_SEEN;
7041 	  t = DECL_VALUE_EXPR (decl);
7042 	  gcc_assert (TREE_CODE (t) == INDIRECT_REF);
7043 	  t = TREE_OPERAND (t, 0);
7044 	  gcc_assert (DECL_P (t));
7045 	  omp_add_variable (ctx, t, nflags);
7046 	}
7047 
7048       /* Add all of the variable and type parameters (which should have
7049 	 been gimplified to a formal temporary) as FIRSTPRIVATE.  */
7050       omp_firstprivatize_variable (ctx, DECL_SIZE_UNIT (decl));
7051       omp_firstprivatize_variable (ctx, DECL_SIZE (decl));
7052       omp_firstprivatize_type_sizes (ctx, TREE_TYPE (decl));
7053 
7054       /* The variable-sized variable itself is never SHARED, only some form
7055 	 of PRIVATE.  The sharing would take place via the pointer variable
7056 	 which we remapped above.  */
7057       if (flags & GOVD_SHARED)
7058 	flags = GOVD_SHARED | GOVD_DEBUG_PRIVATE
7059 		| (flags & (GOVD_SEEN | GOVD_EXPLICIT));
7060 
7061       /* We're going to make use of the TYPE_SIZE_UNIT at least in the
7062 	 alloca statement we generate for the variable, so make sure it
7063 	 is available.  This isn't automatically needed for the SHARED
7064 	 case, since we won't be allocating local storage then.
7065 	 For local variables TYPE_SIZE_UNIT might not be gimplified yet,
7066 	 in this case omp_notice_variable will be called later
7067 	 on when it is gimplified.  */
7068       else if (! (flags & (GOVD_LOCAL | GOVD_MAP))
7069 	       && DECL_P (TYPE_SIZE_UNIT (TREE_TYPE (decl))))
7070 	omp_notice_variable (ctx, TYPE_SIZE_UNIT (TREE_TYPE (decl)), true);
7071     }
7072   else if ((flags & (GOVD_MAP | GOVD_LOCAL)) == 0
7073 	   && lang_hooks.decls.omp_privatize_by_reference (decl))
7074     {
7075       omp_firstprivatize_type_sizes (ctx, TREE_TYPE (decl));
7076 
7077       /* Similar to the direct variable sized case above, we'll need the
7078 	 size of references being privatized.  */
7079       if ((flags & GOVD_SHARED) == 0)
7080 	{
7081 	  t = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)));
7082 	  if (t && DECL_P (t))
7083 	    omp_notice_variable (ctx, t, true);
7084 	}
7085     }
7086 
7087   if (n != NULL)
7088     n->value |= flags;
7089   else
7090     splay_tree_insert (ctx->variables, (splay_tree_key)decl, flags);
7091 
7092   /* For reductions clauses in OpenACC loop directives, by default create a
7093      copy clause on the enclosing parallel construct for carrying back the
7094      results.  */
7095   if (ctx->region_type == ORT_ACC && (flags & GOVD_REDUCTION))
7096     {
7097       struct gimplify_omp_ctx *outer_ctx = ctx->outer_context;
7098       while (outer_ctx)
7099 	{
7100 	  n = splay_tree_lookup (outer_ctx->variables, (splay_tree_key)decl);
7101 	  if (n != NULL)
7102 	    {
7103 	      /* Ignore local variables and explicitly declared clauses.  */
7104 	      if (n->value & (GOVD_LOCAL | GOVD_EXPLICIT))
7105 		break;
7106 	      else if (outer_ctx->region_type == ORT_ACC_KERNELS)
7107 		{
7108 		  /* According to the OpenACC spec, such a reduction variable
7109 		     should already have a copy map on a kernels construct,
7110 		     verify that here.  */
7111 		  gcc_assert (!(n->value & GOVD_FIRSTPRIVATE)
7112 			      && (n->value & GOVD_MAP));
7113 		}
7114 	      else if (outer_ctx->region_type == ORT_ACC_PARALLEL)
7115 		{
7116 		  /* Remove firstprivate and make it a copy map.  */
7117 		  n->value &= ~GOVD_FIRSTPRIVATE;
7118 		  n->value |= GOVD_MAP;
7119 		}
7120 	    }
7121 	  else if (outer_ctx->region_type == ORT_ACC_PARALLEL)
7122 	    {
7123 	      splay_tree_insert (outer_ctx->variables, (splay_tree_key)decl,
7124 				 GOVD_MAP | GOVD_SEEN);
7125 	      break;
7126 	    }
7127 	  outer_ctx = outer_ctx->outer_context;
7128 	}
7129     }
7130 }
7131 
7132 /* Notice a threadprivate variable DECL used in OMP context CTX.
7133    This just prints out diagnostics about threadprivate variable uses
7134    in untied tasks.  If DECL2 is non-NULL, prevent this warning
7135    on that variable.  */
7136 
7137 static bool
omp_notice_threadprivate_variable(struct gimplify_omp_ctx * ctx,tree decl,tree decl2)7138 omp_notice_threadprivate_variable (struct gimplify_omp_ctx *ctx, tree decl,
7139 				   tree decl2)
7140 {
7141   splay_tree_node n;
7142   struct gimplify_omp_ctx *octx;
7143 
7144   for (octx = ctx; octx; octx = octx->outer_context)
7145     if ((octx->region_type & ORT_TARGET) != 0
7146 	|| octx->order_concurrent)
7147       {
7148 	n = splay_tree_lookup (octx->variables, (splay_tree_key)decl);
7149 	if (n == NULL)
7150 	  {
7151 	    if (octx->order_concurrent)
7152 	      {
7153 		error ("threadprivate variable %qE used in a region with"
7154 		       " %<order(concurrent)%> clause", DECL_NAME (decl));
7155 		inform (octx->location, "enclosing region");
7156 	      }
7157 	    else
7158 	      {
7159 		error ("threadprivate variable %qE used in target region",
7160 		       DECL_NAME (decl));
7161 		inform (octx->location, "enclosing target region");
7162 	      }
7163 	    splay_tree_insert (octx->variables, (splay_tree_key)decl, 0);
7164 	  }
7165 	if (decl2)
7166 	  splay_tree_insert (octx->variables, (splay_tree_key)decl2, 0);
7167       }
7168 
7169   if (ctx->region_type != ORT_UNTIED_TASK)
7170     return false;
7171   n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
7172   if (n == NULL)
7173     {
7174       error ("threadprivate variable %qE used in untied task",
7175 	     DECL_NAME (decl));
7176       inform (ctx->location, "enclosing task");
7177       splay_tree_insert (ctx->variables, (splay_tree_key)decl, 0);
7178     }
7179   if (decl2)
7180     splay_tree_insert (ctx->variables, (splay_tree_key)decl2, 0);
7181   return false;
7182 }
7183 
7184 /* Return true if global var DECL is device resident.  */
7185 
7186 static bool
device_resident_p(tree decl)7187 device_resident_p (tree decl)
7188 {
7189   tree attr = lookup_attribute ("oacc declare target", DECL_ATTRIBUTES (decl));
7190 
7191   if (!attr)
7192     return false;
7193 
7194   for (tree t = TREE_VALUE (attr); t; t = TREE_PURPOSE (t))
7195     {
7196       tree c = TREE_VALUE (t);
7197       if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DEVICE_RESIDENT)
7198 	return true;
7199     }
7200 
7201   return false;
7202 }
7203 
7204 /* Return true if DECL has an ACC DECLARE attribute.  */
7205 
7206 static bool
is_oacc_declared(tree decl)7207 is_oacc_declared (tree decl)
7208 {
7209   tree t = TREE_CODE (decl) == MEM_REF ? TREE_OPERAND (decl, 0) : decl;
7210   tree declared = lookup_attribute ("oacc declare target", DECL_ATTRIBUTES (t));
7211   return declared != NULL_TREE;
7212 }
7213 
7214 /* Determine outer default flags for DECL mentioned in an OMP region
7215    but not declared in an enclosing clause.
7216 
7217    ??? Some compiler-generated variables (like SAVE_EXPRs) could be
7218    remapped firstprivate instead of shared.  To some extent this is
7219    addressed in omp_firstprivatize_type_sizes, but not
7220    effectively.  */
7221 
7222 static unsigned
omp_default_clause(struct gimplify_omp_ctx * ctx,tree decl,bool in_code,unsigned flags)7223 omp_default_clause (struct gimplify_omp_ctx *ctx, tree decl,
7224 		    bool in_code, unsigned flags)
7225 {
7226   enum omp_clause_default_kind default_kind = ctx->default_kind;
7227   enum omp_clause_default_kind kind;
7228 
7229   kind = lang_hooks.decls.omp_predetermined_sharing (decl);
7230   if (ctx->region_type & ORT_TASK)
7231     {
7232       tree detach_clause = omp_find_clause (ctx->clauses, OMP_CLAUSE_DETACH);
7233 
7234       /* The event-handle specified by a detach clause should always be firstprivate,
7235 	 regardless of the current default.  */
7236       if (detach_clause && OMP_CLAUSE_DECL (detach_clause) == decl)
7237 	kind = OMP_CLAUSE_DEFAULT_FIRSTPRIVATE;
7238     }
7239   if (kind != OMP_CLAUSE_DEFAULT_UNSPECIFIED)
7240     default_kind = kind;
7241   else if (VAR_P (decl) && TREE_STATIC (decl) && DECL_IN_CONSTANT_POOL (decl))
7242     default_kind = OMP_CLAUSE_DEFAULT_SHARED;
7243 
7244   switch (default_kind)
7245     {
7246     case OMP_CLAUSE_DEFAULT_NONE:
7247       {
7248 	const char *rtype;
7249 
7250 	if (ctx->region_type & ORT_PARALLEL)
7251 	  rtype = "parallel";
7252 	else if ((ctx->region_type & ORT_TASKLOOP) == ORT_TASKLOOP)
7253 	  rtype = "taskloop";
7254 	else if (ctx->region_type & ORT_TASK)
7255 	  rtype = "task";
7256 	else if (ctx->region_type & ORT_TEAMS)
7257 	  rtype = "teams";
7258 	else
7259 	  gcc_unreachable ();
7260 
7261 	error ("%qE not specified in enclosing %qs",
7262 	       DECL_NAME (lang_hooks.decls.omp_report_decl (decl)), rtype);
7263 	inform (ctx->location, "enclosing %qs", rtype);
7264       }
7265       /* FALLTHRU */
7266     case OMP_CLAUSE_DEFAULT_SHARED:
7267       flags |= GOVD_SHARED;
7268       break;
7269     case OMP_CLAUSE_DEFAULT_PRIVATE:
7270       flags |= GOVD_PRIVATE;
7271       break;
7272     case OMP_CLAUSE_DEFAULT_FIRSTPRIVATE:
7273       flags |= GOVD_FIRSTPRIVATE;
7274       break;
7275     case OMP_CLAUSE_DEFAULT_UNSPECIFIED:
7276       /* decl will be either GOVD_FIRSTPRIVATE or GOVD_SHARED.  */
7277       gcc_assert ((ctx->region_type & ORT_TASK) != 0);
7278       if (struct gimplify_omp_ctx *octx = ctx->outer_context)
7279 	{
7280 	  omp_notice_variable (octx, decl, in_code);
7281 	  for (; octx; octx = octx->outer_context)
7282 	    {
7283 	      splay_tree_node n2;
7284 
7285 	      n2 = splay_tree_lookup (octx->variables, (splay_tree_key) decl);
7286 	      if ((octx->region_type & (ORT_TARGET_DATA | ORT_TARGET)) != 0
7287 		  && (n2 == NULL || (n2->value & GOVD_DATA_SHARE_CLASS) == 0))
7288 		continue;
7289 	      if (n2 && (n2->value & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED)
7290 		{
7291 		  flags |= GOVD_FIRSTPRIVATE;
7292 		  goto found_outer;
7293 		}
7294 	      if ((octx->region_type & (ORT_PARALLEL | ORT_TEAMS)) != 0)
7295 		{
7296 		  flags |= GOVD_SHARED;
7297 		  goto found_outer;
7298 		}
7299 	    }
7300 	}
7301 
7302       if (TREE_CODE (decl) == PARM_DECL
7303 	  || (!is_global_var (decl)
7304 	      && DECL_CONTEXT (decl) == current_function_decl))
7305 	flags |= GOVD_FIRSTPRIVATE;
7306       else
7307 	flags |= GOVD_SHARED;
7308     found_outer:
7309       break;
7310 
7311     default:
7312       gcc_unreachable ();
7313     }
7314 
7315   return flags;
7316 }
7317 
7318 
7319 /* Determine outer default flags for DECL mentioned in an OACC region
7320    but not declared in an enclosing clause.  */
7321 
7322 static unsigned
oacc_default_clause(struct gimplify_omp_ctx * ctx,tree decl,unsigned flags)7323 oacc_default_clause (struct gimplify_omp_ctx *ctx, tree decl, unsigned flags)
7324 {
7325   const char *rkind;
7326   bool on_device = false;
7327   bool is_private = false;
7328   bool declared = is_oacc_declared (decl);
7329   tree type = TREE_TYPE (decl);
7330 
7331   if (lang_hooks.decls.omp_privatize_by_reference (decl))
7332     type = TREE_TYPE (type);
7333 
7334   /* For Fortran COMMON blocks, only used variables in those blocks are
7335      transfered and remapped.  The block itself will have a private clause to
7336      avoid transfering the data twice.
7337      The hook evaluates to false by default.  For a variable in Fortran's COMMON
7338      or EQUIVALENCE block, returns 'true' (as we have shared=false) - as only
7339      the variables in such a COMMON/EQUIVALENCE block shall be privatized not
7340      the whole block.  For C++ and Fortran, it can also be true under certain
7341      other conditions, if DECL_HAS_VALUE_EXPR.  */
7342   if (RECORD_OR_UNION_TYPE_P (type))
7343     is_private = lang_hooks.decls.omp_disregard_value_expr (decl, false);
7344 
7345   if ((ctx->region_type & (ORT_ACC_PARALLEL | ORT_ACC_KERNELS)) != 0
7346       && is_global_var (decl)
7347       && device_resident_p (decl)
7348       && !is_private)
7349     {
7350       on_device = true;
7351       flags |= GOVD_MAP_TO_ONLY;
7352     }
7353 
7354   switch (ctx->region_type)
7355     {
7356     case ORT_ACC_KERNELS:
7357       rkind = "kernels";
7358 
7359       if (is_private)
7360 	flags |= GOVD_FIRSTPRIVATE;
7361       else if (AGGREGATE_TYPE_P (type))
7362 	{
7363 	  /* Aggregates default to 'present_or_copy', or 'present'.  */
7364 	  if (ctx->default_kind != OMP_CLAUSE_DEFAULT_PRESENT)
7365 	    flags |= GOVD_MAP;
7366 	  else
7367 	    flags |= GOVD_MAP | GOVD_MAP_FORCE_PRESENT;
7368 	}
7369       else
7370 	/* Scalars default to 'copy'.  */
7371 	flags |= GOVD_MAP | GOVD_MAP_FORCE;
7372 
7373       break;
7374 
7375     case ORT_ACC_PARALLEL:
7376     case ORT_ACC_SERIAL:
7377       rkind = ctx->region_type == ORT_ACC_PARALLEL ? "parallel" : "serial";
7378 
7379       if (is_private)
7380 	flags |= GOVD_FIRSTPRIVATE;
7381       else if (on_device || declared)
7382 	flags |= GOVD_MAP;
7383       else if (AGGREGATE_TYPE_P (type))
7384 	{
7385 	  /* Aggregates default to 'present_or_copy', or 'present'.  */
7386 	  if (ctx->default_kind != OMP_CLAUSE_DEFAULT_PRESENT)
7387 	    flags |= GOVD_MAP;
7388 	  else
7389 	    flags |= GOVD_MAP | GOVD_MAP_FORCE_PRESENT;
7390 	}
7391       else
7392 	/* Scalars default to 'firstprivate'.  */
7393 	flags |= GOVD_FIRSTPRIVATE;
7394 
7395       break;
7396 
7397     default:
7398       gcc_unreachable ();
7399     }
7400 
7401   if (DECL_ARTIFICIAL (decl))
7402     ; /* We can get compiler-generated decls, and should not complain
7403 	 about them.  */
7404   else if (ctx->default_kind == OMP_CLAUSE_DEFAULT_NONE)
7405     {
7406       error ("%qE not specified in enclosing OpenACC %qs construct",
7407 	     DECL_NAME (lang_hooks.decls.omp_report_decl (decl)), rkind);
7408       inform (ctx->location, "enclosing OpenACC %qs construct", rkind);
7409     }
7410   else if (ctx->default_kind == OMP_CLAUSE_DEFAULT_PRESENT)
7411     ; /* Handled above.  */
7412   else
7413     gcc_checking_assert (ctx->default_kind == OMP_CLAUSE_DEFAULT_SHARED);
7414 
7415   return flags;
7416 }
7417 
7418 /* Record the fact that DECL was used within the OMP context CTX.
7419    IN_CODE is true when real code uses DECL, and false when we should
7420    merely emit default(none) errors.  Return true if DECL is going to
7421    be remapped and thus DECL shouldn't be gimplified into its
7422    DECL_VALUE_EXPR (if any).  */
7423 
7424 static bool
omp_notice_variable(struct gimplify_omp_ctx * ctx,tree decl,bool in_code)7425 omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
7426 {
7427   splay_tree_node n;
7428   unsigned flags = in_code ? GOVD_SEEN : 0;
7429   bool ret = false, shared;
7430 
7431   if (error_operand_p (decl))
7432     return false;
7433 
7434   if (ctx->region_type == ORT_NONE)
7435     return lang_hooks.decls.omp_disregard_value_expr (decl, false);
7436 
7437   if (is_global_var (decl))
7438     {
7439       /* Threadprivate variables are predetermined.  */
7440       if (DECL_THREAD_LOCAL_P (decl))
7441 	return omp_notice_threadprivate_variable (ctx, decl, NULL_TREE);
7442 
7443       if (DECL_HAS_VALUE_EXPR_P (decl))
7444 	{
7445 	  if (ctx->region_type & ORT_ACC)
7446 	    /* For OpenACC, defer expansion of value to avoid transfering
7447 	       privatized common block data instead of im-/explicitly transfered
7448 	       variables which are in common blocks.  */
7449 	    ;
7450 	  else
7451 	    {
7452 	      tree value = get_base_address (DECL_VALUE_EXPR (decl));
7453 
7454 	      if (value && DECL_P (value) && DECL_THREAD_LOCAL_P (value))
7455 		return omp_notice_threadprivate_variable (ctx, decl, value);
7456 	    }
7457 	}
7458 
7459       if (gimplify_omp_ctxp->outer_context == NULL
7460 	  && VAR_P (decl)
7461 	  && oacc_get_fn_attrib (current_function_decl))
7462 	{
7463 	  location_t loc = DECL_SOURCE_LOCATION (decl);
7464 
7465 	  if (lookup_attribute ("omp declare target link",
7466 				DECL_ATTRIBUTES (decl)))
7467 	    {
7468 	      error_at (loc,
7469 			"%qE with %<link%> clause used in %<routine%> function",
7470 			DECL_NAME (decl));
7471 	      return false;
7472 	    }
7473 	  else if (!lookup_attribute ("omp declare target",
7474 				      DECL_ATTRIBUTES (decl)))
7475 	    {
7476 	      error_at (loc,
7477 			"%qE requires a %<declare%> directive for use "
7478 			"in a %<routine%> function", DECL_NAME (decl));
7479 	      return false;
7480 	    }
7481 	}
7482     }
7483 
7484   n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
7485   if ((ctx->region_type & ORT_TARGET) != 0)
7486     {
7487       if (ctx->region_type & ORT_ACC)
7488 	/* For OpenACC, as remarked above, defer expansion.  */
7489 	shared = false;
7490       else
7491 	shared = true;
7492 
7493       ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
7494       if (n == NULL)
7495 	{
7496 	  unsigned nflags = flags;
7497 	  if ((ctx->region_type & ORT_ACC) == 0)
7498 	    {
7499 	      bool is_declare_target = false;
7500 	      if (is_global_var (decl)
7501 		  && varpool_node::get_create (decl)->offloadable)
7502 		{
7503 		  struct gimplify_omp_ctx *octx;
7504 		  for (octx = ctx->outer_context;
7505 		       octx; octx = octx->outer_context)
7506 		    {
7507 		      n = splay_tree_lookup (octx->variables,
7508 					     (splay_tree_key)decl);
7509 		      if (n
7510 			  && (n->value & GOVD_DATA_SHARE_CLASS) != GOVD_SHARED
7511 			  && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
7512 			break;
7513 		    }
7514 		  is_declare_target = octx == NULL;
7515 		}
7516 	      if (!is_declare_target)
7517 		{
7518 		  int gdmk;
7519 		  enum omp_clause_defaultmap_kind kind;
7520 		  if (TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE
7521 		      || (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE
7522 			  && (TREE_CODE (TREE_TYPE (TREE_TYPE (decl)))
7523 			      == POINTER_TYPE)))
7524 		    gdmk = GDMK_POINTER;
7525 		  else if (lang_hooks.decls.omp_scalar_p (decl))
7526 		    gdmk = GDMK_SCALAR;
7527 		  else
7528 		    gdmk = GDMK_AGGREGATE;
7529 		  kind = lang_hooks.decls.omp_predetermined_mapping (decl);
7530 		  if (kind != OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED)
7531 		    {
7532 		      if (kind == OMP_CLAUSE_DEFAULTMAP_FIRSTPRIVATE)
7533 			nflags |= GOVD_FIRSTPRIVATE;
7534 		      else if (kind == OMP_CLAUSE_DEFAULTMAP_TO)
7535 			nflags |= GOVD_MAP | GOVD_MAP_TO_ONLY;
7536 		      else
7537 			gcc_unreachable ();
7538 		    }
7539 		  else if (ctx->defaultmap[gdmk] == 0)
7540 		    {
7541 		      tree d = lang_hooks.decls.omp_report_decl (decl);
7542 		      error ("%qE not specified in enclosing %<target%>",
7543 			     DECL_NAME (d));
7544 		      inform (ctx->location, "enclosing %<target%>");
7545 		    }
7546 		  else if (ctx->defaultmap[gdmk]
7547 			   & (GOVD_MAP_0LEN_ARRAY | GOVD_FIRSTPRIVATE))
7548 		    nflags |= ctx->defaultmap[gdmk];
7549 		  else
7550 		    {
7551 		      gcc_assert (ctx->defaultmap[gdmk] & GOVD_MAP);
7552 		      nflags |= ctx->defaultmap[gdmk] & ~GOVD_MAP;
7553 		    }
7554 		}
7555 	    }
7556 
7557 	  struct gimplify_omp_ctx *octx = ctx->outer_context;
7558 	  if ((ctx->region_type & ORT_ACC) && octx)
7559 	    {
7560 	      /* Look in outer OpenACC contexts, to see if there's a
7561 		 data attribute for this variable.  */
7562 	      omp_notice_variable (octx, decl, in_code);
7563 
7564 	      for (; octx; octx = octx->outer_context)
7565 		{
7566 		  if (!(octx->region_type & (ORT_TARGET_DATA | ORT_TARGET)))
7567 		    break;
7568 		  splay_tree_node n2
7569 		    = splay_tree_lookup (octx->variables,
7570 					 (splay_tree_key) decl);
7571 		  if (n2)
7572 		    {
7573 		      if (octx->region_type == ORT_ACC_HOST_DATA)
7574 		        error ("variable %qE declared in enclosing "
7575 			       "%<host_data%> region", DECL_NAME (decl));
7576 		      nflags |= GOVD_MAP;
7577 		      if (octx->region_type == ORT_ACC_DATA
7578 			  && (n2->value & GOVD_MAP_0LEN_ARRAY))
7579 			nflags |= GOVD_MAP_0LEN_ARRAY;
7580 		      goto found_outer;
7581 		    }
7582 		}
7583 	    }
7584 
7585 	  if ((nflags & ~(GOVD_MAP_TO_ONLY | GOVD_MAP_FROM_ONLY
7586 			  | GOVD_MAP_ALLOC_ONLY)) == flags)
7587 	    {
7588 	      tree type = TREE_TYPE (decl);
7589 
7590 	      if (gimplify_omp_ctxp->target_firstprivatize_array_bases
7591 		  && lang_hooks.decls.omp_privatize_by_reference (decl))
7592 		type = TREE_TYPE (type);
7593 	      if (!lang_hooks.types.omp_mappable_type (type))
7594 		{
7595 		  error ("%qD referenced in target region does not have "
7596 			 "a mappable type", decl);
7597 		  nflags |= GOVD_MAP | GOVD_EXPLICIT;
7598 		}
7599 	      else
7600 		{
7601 		  if ((ctx->region_type & ORT_ACC) != 0)
7602 		    nflags = oacc_default_clause (ctx, decl, flags);
7603 		  else
7604 		    nflags |= GOVD_MAP;
7605 		}
7606 	    }
7607 	found_outer:
7608 	  omp_add_variable (ctx, decl, nflags);
7609 	}
7610       else
7611 	{
7612 	  /* If nothing changed, there's nothing left to do.  */
7613 	  if ((n->value & flags) == flags)
7614 	    return ret;
7615 	  flags |= n->value;
7616 	  n->value = flags;
7617 	}
7618       goto do_outer;
7619     }
7620 
7621   if (n == NULL)
7622     {
7623       if (ctx->region_type == ORT_WORKSHARE
7624 	  || ctx->region_type == ORT_TASKGROUP
7625 	  || ctx->region_type == ORT_SIMD
7626 	  || ctx->region_type == ORT_ACC
7627 	  || (ctx->region_type & ORT_TARGET_DATA) != 0)
7628 	goto do_outer;
7629 
7630       flags = omp_default_clause (ctx, decl, in_code, flags);
7631 
7632       if ((flags & GOVD_PRIVATE)
7633 	  && lang_hooks.decls.omp_private_outer_ref (decl))
7634 	flags |= GOVD_PRIVATE_OUTER_REF;
7635 
7636       omp_add_variable (ctx, decl, flags);
7637 
7638       shared = (flags & GOVD_SHARED) != 0;
7639       ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
7640       goto do_outer;
7641     }
7642 
7643   /* Don't mark as GOVD_SEEN addressable temporaries seen only in simd
7644      lb, b or incr expressions, those shouldn't be turned into simd arrays.  */
7645   if (ctx->region_type == ORT_SIMD
7646       && ctx->in_for_exprs
7647       && ((n->value & (GOVD_PRIVATE | GOVD_SEEN | GOVD_EXPLICIT))
7648 	  == GOVD_PRIVATE))
7649     flags &= ~GOVD_SEEN;
7650 
7651   if ((n->value & (GOVD_SEEN | GOVD_LOCAL)) == 0
7652       && (flags & (GOVD_SEEN | GOVD_LOCAL)) == GOVD_SEEN
7653       && DECL_SIZE (decl))
7654     {
7655       if (TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
7656 	{
7657 	  splay_tree_node n2;
7658 	  tree t = DECL_VALUE_EXPR (decl);
7659 	  gcc_assert (TREE_CODE (t) == INDIRECT_REF);
7660 	  t = TREE_OPERAND (t, 0);
7661 	  gcc_assert (DECL_P (t));
7662 	  n2 = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
7663 	  n2->value |= GOVD_SEEN;
7664 	}
7665       else if (lang_hooks.decls.omp_privatize_by_reference (decl)
7666 	       && TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)))
7667 	       && (TREE_CODE (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl))))
7668 		   != INTEGER_CST))
7669 	{
7670 	  splay_tree_node n2;
7671 	  tree t = TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl)));
7672 	  gcc_assert (DECL_P (t));
7673 	  n2 = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
7674 	  if (n2)
7675 	    omp_notice_variable (ctx, t, true);
7676 	}
7677     }
7678 
7679   if (ctx->region_type & ORT_ACC)
7680     /* For OpenACC, as remarked above, defer expansion.  */
7681     shared = false;
7682   else
7683     shared = ((flags | n->value) & GOVD_SHARED) != 0;
7684   ret = lang_hooks.decls.omp_disregard_value_expr (decl, shared);
7685 
7686   /* If nothing changed, there's nothing left to do.  */
7687   if ((n->value & flags) == flags)
7688     return ret;
7689   flags |= n->value;
7690   n->value = flags;
7691 
7692  do_outer:
7693   /* If the variable is private in the current context, then we don't
7694      need to propagate anything to an outer context.  */
7695   if ((flags & GOVD_PRIVATE) && !(flags & GOVD_PRIVATE_OUTER_REF))
7696     return ret;
7697   if ((flags & (GOVD_LINEAR | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
7698       == (GOVD_LINEAR | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
7699     return ret;
7700   if ((flags & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
7701 		| GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
7702       == (GOVD_LASTPRIVATE | GOVD_LINEAR_LASTPRIVATE_NO_OUTER))
7703     return ret;
7704   if (ctx->outer_context
7705       && omp_notice_variable (ctx->outer_context, decl, in_code))
7706     return true;
7707   return ret;
7708 }
7709 
7710 /* Verify that DECL is private within CTX.  If there's specific information
7711    to the contrary in the innermost scope, generate an error.  */
7712 
7713 static bool
omp_is_private(struct gimplify_omp_ctx * ctx,tree decl,int simd)7714 omp_is_private (struct gimplify_omp_ctx *ctx, tree decl, int simd)
7715 {
7716   splay_tree_node n;
7717 
7718   n = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
7719   if (n != NULL)
7720     {
7721       if (n->value & GOVD_SHARED)
7722 	{
7723 	  if (ctx == gimplify_omp_ctxp)
7724 	    {
7725 	      if (simd)
7726 		error ("iteration variable %qE is predetermined linear",
7727 		       DECL_NAME (decl));
7728 	      else
7729 		error ("iteration variable %qE should be private",
7730 		       DECL_NAME (decl));
7731 	      n->value = GOVD_PRIVATE;
7732 	      return true;
7733 	    }
7734 	  else
7735 	    return false;
7736 	}
7737       else if ((n->value & GOVD_EXPLICIT) != 0
7738 	       && (ctx == gimplify_omp_ctxp
7739 		   || (ctx->region_type == ORT_COMBINED_PARALLEL
7740 		       && gimplify_omp_ctxp->outer_context == ctx)))
7741 	{
7742 	  if ((n->value & GOVD_FIRSTPRIVATE) != 0)
7743 	    error ("iteration variable %qE should not be firstprivate",
7744 		   DECL_NAME (decl));
7745 	  else if ((n->value & GOVD_REDUCTION) != 0)
7746 	    error ("iteration variable %qE should not be reduction",
7747 		   DECL_NAME (decl));
7748 	  else if (simd != 1 && (n->value & GOVD_LINEAR) != 0)
7749 	    error ("iteration variable %qE should not be linear",
7750 		   DECL_NAME (decl));
7751 	}
7752       return (ctx == gimplify_omp_ctxp
7753 	      || (ctx->region_type == ORT_COMBINED_PARALLEL
7754 		  && gimplify_omp_ctxp->outer_context == ctx));
7755     }
7756 
7757   if (ctx->region_type != ORT_WORKSHARE
7758       && ctx->region_type != ORT_TASKGROUP
7759       && ctx->region_type != ORT_SIMD
7760       && ctx->region_type != ORT_ACC)
7761     return false;
7762   else if (ctx->outer_context)
7763     return omp_is_private (ctx->outer_context, decl, simd);
7764   return false;
7765 }
7766 
7767 /* Return true if DECL is private within a parallel region
7768    that binds to the current construct's context or in parallel
7769    region's REDUCTION clause.  */
7770 
7771 static bool
omp_check_private(struct gimplify_omp_ctx * ctx,tree decl,bool copyprivate)7772 omp_check_private (struct gimplify_omp_ctx *ctx, tree decl, bool copyprivate)
7773 {
7774   splay_tree_node n;
7775 
7776   do
7777     {
7778       ctx = ctx->outer_context;
7779       if (ctx == NULL)
7780 	{
7781 	  if (is_global_var (decl))
7782 	    return false;
7783 
7784 	  /* References might be private, but might be shared too,
7785 	     when checking for copyprivate, assume they might be
7786 	     private, otherwise assume they might be shared.  */
7787 	  if (copyprivate)
7788 	    return true;
7789 
7790 	  if (lang_hooks.decls.omp_privatize_by_reference (decl))
7791 	    return false;
7792 
7793 	  /* Treat C++ privatized non-static data members outside
7794 	     of the privatization the same.  */
7795 	  if (omp_member_access_dummy_var (decl))
7796 	    return false;
7797 
7798 	  return true;
7799 	}
7800 
7801       n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
7802 
7803       if ((ctx->region_type & (ORT_TARGET | ORT_TARGET_DATA)) != 0
7804 	  && (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0))
7805 	{
7806 	  if ((ctx->region_type & ORT_TARGET_DATA) != 0
7807 	      || n == NULL
7808 	      || (n->value & GOVD_MAP) == 0)
7809 	    continue;
7810 	  return false;
7811 	}
7812 
7813       if (n != NULL)
7814 	{
7815 	  if ((n->value & GOVD_LOCAL) != 0
7816 	      && omp_member_access_dummy_var (decl))
7817 	    return false;
7818 	  return (n->value & GOVD_SHARED) == 0;
7819 	}
7820 
7821       if (ctx->region_type == ORT_WORKSHARE
7822 	  || ctx->region_type == ORT_TASKGROUP
7823 	  || ctx->region_type == ORT_SIMD
7824 	  || ctx->region_type == ORT_ACC)
7825 	continue;
7826 
7827       break;
7828     }
7829   while (1);
7830   return false;
7831 }
7832 
7833 /* Callback for walk_tree to find a DECL_EXPR for the given DECL.  */
7834 
7835 static tree
find_decl_expr(tree * tp,int * walk_subtrees,void * data)7836 find_decl_expr (tree *tp, int *walk_subtrees, void *data)
7837 {
7838   tree t = *tp;
7839 
7840   /* If this node has been visited, unmark it and keep looking.  */
7841   if (TREE_CODE (t) == DECL_EXPR && DECL_EXPR_DECL (t) == (tree) data)
7842     return t;
7843 
7844   if (IS_TYPE_OR_DECL_P (t))
7845     *walk_subtrees = 0;
7846   return NULL_TREE;
7847 }
7848 
7849 /* If *LIST_P contains any OpenMP depend clauses with iterators,
7850    lower all the depend clauses by populating corresponding depend
7851    array.  Returns 0 if there are no such depend clauses, or
7852    2 if all depend clauses should be removed, 1 otherwise.  */
7853 
7854 static int
gimplify_omp_depend(tree * list_p,gimple_seq * pre_p)7855 gimplify_omp_depend (tree *list_p, gimple_seq *pre_p)
7856 {
7857   tree c;
7858   gimple *g;
7859   size_t n[4] = { 0, 0, 0, 0 };
7860   bool unused[4];
7861   tree counts[4] = { NULL_TREE, NULL_TREE, NULL_TREE, NULL_TREE };
7862   tree last_iter = NULL_TREE, last_count = NULL_TREE;
7863   size_t i, j;
7864   location_t first_loc = UNKNOWN_LOCATION;
7865 
7866   for (c = *list_p; c; c = OMP_CLAUSE_CHAIN (c))
7867     if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND)
7868       {
7869 	switch (OMP_CLAUSE_DEPEND_KIND (c))
7870 	  {
7871 	  case OMP_CLAUSE_DEPEND_IN:
7872 	    i = 2;
7873 	    break;
7874 	  case OMP_CLAUSE_DEPEND_OUT:
7875 	  case OMP_CLAUSE_DEPEND_INOUT:
7876 	    i = 0;
7877 	    break;
7878 	  case OMP_CLAUSE_DEPEND_MUTEXINOUTSET:
7879 	    i = 1;
7880 	    break;
7881 	  case OMP_CLAUSE_DEPEND_DEPOBJ:
7882 	    i = 3;
7883 	    break;
7884 	  case OMP_CLAUSE_DEPEND_SOURCE:
7885 	  case OMP_CLAUSE_DEPEND_SINK:
7886 	    continue;
7887 	  default:
7888 	    gcc_unreachable ();
7889 	  }
7890 	tree t = OMP_CLAUSE_DECL (c);
7891 	if (first_loc == UNKNOWN_LOCATION)
7892 	  first_loc = OMP_CLAUSE_LOCATION (c);
7893 	if (TREE_CODE (t) == TREE_LIST
7894 	    && TREE_PURPOSE (t)
7895 	    && TREE_CODE (TREE_PURPOSE (t)) == TREE_VEC)
7896 	  {
7897 	    if (TREE_PURPOSE (t) != last_iter)
7898 	      {
7899 		tree tcnt = size_one_node;
7900 		for (tree it = TREE_PURPOSE (t); it; it = TREE_CHAIN (it))
7901 		  {
7902 		    if (gimplify_expr (&TREE_VEC_ELT (it, 1), pre_p, NULL,
7903 				       is_gimple_val, fb_rvalue) == GS_ERROR
7904 			|| gimplify_expr (&TREE_VEC_ELT (it, 2), pre_p, NULL,
7905 					  is_gimple_val, fb_rvalue) == GS_ERROR
7906 			|| gimplify_expr (&TREE_VEC_ELT (it, 3), pre_p, NULL,
7907 					  is_gimple_val, fb_rvalue) == GS_ERROR
7908 			|| (gimplify_expr (&TREE_VEC_ELT (it, 4), pre_p, NULL,
7909 					   is_gimple_val, fb_rvalue)
7910 			    == GS_ERROR))
7911 		      return 2;
7912 		    tree var = TREE_VEC_ELT (it, 0);
7913 		    tree begin = TREE_VEC_ELT (it, 1);
7914 		    tree end = TREE_VEC_ELT (it, 2);
7915 		    tree step = TREE_VEC_ELT (it, 3);
7916 		    tree orig_step = TREE_VEC_ELT (it, 4);
7917 		    tree type = TREE_TYPE (var);
7918 		    tree stype = TREE_TYPE (step);
7919 		    location_t loc = DECL_SOURCE_LOCATION (var);
7920 		    tree endmbegin;
7921 		    /* Compute count for this iterator as
7922 		       orig_step > 0
7923 		       ? (begin < end ? (end - begin + (step - 1)) / step : 0)
7924 		       : (begin > end ? (end - begin + (step + 1)) / step : 0)
7925 		       and compute product of those for the entire depend
7926 		       clause.  */
7927 		    if (POINTER_TYPE_P (type))
7928 		      endmbegin = fold_build2_loc (loc, POINTER_DIFF_EXPR,
7929 						   stype, end, begin);
7930 		    else
7931 		      endmbegin = fold_build2_loc (loc, MINUS_EXPR, type,
7932 						   end, begin);
7933 		    tree stepm1 = fold_build2_loc (loc, MINUS_EXPR, stype,
7934 						   step,
7935 						   build_int_cst (stype, 1));
7936 		    tree stepp1 = fold_build2_loc (loc, PLUS_EXPR, stype, step,
7937 						   build_int_cst (stype, 1));
7938 		    tree pos = fold_build2_loc (loc, PLUS_EXPR, stype,
7939 						unshare_expr (endmbegin),
7940 						stepm1);
7941 		    pos = fold_build2_loc (loc, TRUNC_DIV_EXPR, stype,
7942 					   pos, step);
7943 		    tree neg = fold_build2_loc (loc, PLUS_EXPR, stype,
7944 						endmbegin, stepp1);
7945 		    if (TYPE_UNSIGNED (stype))
7946 		      {
7947 			neg = fold_build1_loc (loc, NEGATE_EXPR, stype, neg);
7948 			step = fold_build1_loc (loc, NEGATE_EXPR, stype, step);
7949 		      }
7950 		    neg = fold_build2_loc (loc, TRUNC_DIV_EXPR, stype,
7951 					   neg, step);
7952 		    step = NULL_TREE;
7953 		    tree cond = fold_build2_loc (loc, LT_EXPR,
7954 						 boolean_type_node,
7955 						 begin, end);
7956 		    pos = fold_build3_loc (loc, COND_EXPR, stype, cond, pos,
7957 					   build_int_cst (stype, 0));
7958 		    cond = fold_build2_loc (loc, LT_EXPR, boolean_type_node,
7959 					    end, begin);
7960 		    neg = fold_build3_loc (loc, COND_EXPR, stype, cond, neg,
7961 					   build_int_cst (stype, 0));
7962 		    tree osteptype = TREE_TYPE (orig_step);
7963 		    cond = fold_build2_loc (loc, GT_EXPR, boolean_type_node,
7964 					    orig_step,
7965 					    build_int_cst (osteptype, 0));
7966 		    tree cnt = fold_build3_loc (loc, COND_EXPR, stype,
7967 						cond, pos, neg);
7968 		    cnt = fold_convert_loc (loc, sizetype, cnt);
7969 		    if (gimplify_expr (&cnt, pre_p, NULL, is_gimple_val,
7970 				       fb_rvalue) == GS_ERROR)
7971 		      return 2;
7972 		    tcnt = size_binop_loc (loc, MULT_EXPR, tcnt, cnt);
7973 		  }
7974 		if (gimplify_expr (&tcnt, pre_p, NULL, is_gimple_val,
7975 				   fb_rvalue) == GS_ERROR)
7976 		  return 2;
7977 		last_iter = TREE_PURPOSE (t);
7978 		last_count = tcnt;
7979 	      }
7980 	    if (counts[i] == NULL_TREE)
7981 	      counts[i] = last_count;
7982 	    else
7983 	      counts[i] = size_binop_loc (OMP_CLAUSE_LOCATION (c),
7984 					  PLUS_EXPR, counts[i], last_count);
7985 	  }
7986 	else
7987 	  n[i]++;
7988       }
7989   for (i = 0; i < 4; i++)
7990     if (counts[i])
7991       break;
7992   if (i == 4)
7993     return 0;
7994 
7995   tree total = size_zero_node;
7996   for (i = 0; i < 4; i++)
7997     {
7998       unused[i] = counts[i] == NULL_TREE && n[i] == 0;
7999       if (counts[i] == NULL_TREE)
8000 	counts[i] = size_zero_node;
8001       if (n[i])
8002 	counts[i] = size_binop (PLUS_EXPR, counts[i], size_int (n[i]));
8003       if (gimplify_expr (&counts[i], pre_p, NULL, is_gimple_val,
8004 			 fb_rvalue) == GS_ERROR)
8005 	return 2;
8006       total = size_binop (PLUS_EXPR, total, counts[i]);
8007     }
8008 
8009   if (gimplify_expr (&total, pre_p, NULL, is_gimple_val, fb_rvalue)
8010       == GS_ERROR)
8011     return 2;
8012   bool is_old = unused[1] && unused[3];
8013   tree totalpx = size_binop (PLUS_EXPR, unshare_expr (total),
8014 			     size_int (is_old ? 1 : 4));
8015   tree type = build_array_type (ptr_type_node, build_index_type (totalpx));
8016   tree array = create_tmp_var_raw (type);
8017   TREE_ADDRESSABLE (array) = 1;
8018   if (!poly_int_tree_p (totalpx))
8019     {
8020       if (!TYPE_SIZES_GIMPLIFIED (TREE_TYPE (array)))
8021 	gimplify_type_sizes (TREE_TYPE (array), pre_p);
8022       if (gimplify_omp_ctxp)
8023 	{
8024 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
8025 	  while (ctx
8026 		 && (ctx->region_type == ORT_WORKSHARE
8027 		     || ctx->region_type == ORT_TASKGROUP
8028 		     || ctx->region_type == ORT_SIMD
8029 		     || ctx->region_type == ORT_ACC))
8030 	    ctx = ctx->outer_context;
8031 	  if (ctx)
8032 	    omp_add_variable (ctx, array, GOVD_LOCAL | GOVD_SEEN);
8033 	}
8034       gimplify_vla_decl (array, pre_p);
8035     }
8036   else
8037     gimple_add_tmp_var (array);
8038   tree r = build4 (ARRAY_REF, ptr_type_node, array, size_int (0), NULL_TREE,
8039 		   NULL_TREE);
8040   tree tem;
8041   if (!is_old)
8042     {
8043       tem = build2 (MODIFY_EXPR, void_type_node, r,
8044 		    build_int_cst (ptr_type_node, 0));
8045       gimplify_and_add (tem, pre_p);
8046       r = build4 (ARRAY_REF, ptr_type_node, array, size_int (1), NULL_TREE,
8047 		  NULL_TREE);
8048     }
8049   tem = build2 (MODIFY_EXPR, void_type_node, r,
8050 		fold_convert (ptr_type_node, total));
8051   gimplify_and_add (tem, pre_p);
8052   for (i = 1; i < (is_old ? 2 : 4); i++)
8053     {
8054       r = build4 (ARRAY_REF, ptr_type_node, array, size_int (i + !is_old),
8055 		  NULL_TREE, NULL_TREE);
8056       tem = build2 (MODIFY_EXPR, void_type_node, r, counts[i - 1]);
8057       gimplify_and_add (tem, pre_p);
8058     }
8059 
8060   tree cnts[4];
8061   for (j = 4; j; j--)
8062     if (!unused[j - 1])
8063       break;
8064   for (i = 0; i < 4; i++)
8065     {
8066       if (i && (i >= j || unused[i - 1]))
8067 	{
8068 	  cnts[i] = cnts[i - 1];
8069 	  continue;
8070 	}
8071       cnts[i] = create_tmp_var (sizetype);
8072       if (i == 0)
8073 	g = gimple_build_assign (cnts[i], size_int (is_old ? 2 : 5));
8074       else
8075 	{
8076 	  tree t;
8077 	  if (is_old)
8078 	    t = size_binop (PLUS_EXPR, counts[0], size_int (2));
8079 	  else
8080 	    t = size_binop (PLUS_EXPR, cnts[i - 1], counts[i - 1]);
8081 	  if (gimplify_expr (&t, pre_p, NULL, is_gimple_val, fb_rvalue)
8082 	      == GS_ERROR)
8083 	    return 2;
8084 	  g = gimple_build_assign (cnts[i], t);
8085 	}
8086       gimple_seq_add_stmt (pre_p, g);
8087     }
8088 
8089   last_iter = NULL_TREE;
8090   tree last_bind = NULL_TREE;
8091   tree *last_body = NULL;
8092   for (c = *list_p; c; c = OMP_CLAUSE_CHAIN (c))
8093     if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND)
8094       {
8095 	switch (OMP_CLAUSE_DEPEND_KIND (c))
8096 	  {
8097 	  case OMP_CLAUSE_DEPEND_IN:
8098 	    i = 2;
8099 	    break;
8100 	  case OMP_CLAUSE_DEPEND_OUT:
8101 	  case OMP_CLAUSE_DEPEND_INOUT:
8102 	    i = 0;
8103 	    break;
8104 	  case OMP_CLAUSE_DEPEND_MUTEXINOUTSET:
8105 	    i = 1;
8106 	    break;
8107 	  case OMP_CLAUSE_DEPEND_DEPOBJ:
8108 	    i = 3;
8109 	    break;
8110 	  case OMP_CLAUSE_DEPEND_SOURCE:
8111 	  case OMP_CLAUSE_DEPEND_SINK:
8112 	    continue;
8113 	  default:
8114 	    gcc_unreachable ();
8115 	  }
8116 	tree t = OMP_CLAUSE_DECL (c);
8117 	if (TREE_CODE (t) == TREE_LIST
8118 	    && TREE_PURPOSE (t)
8119 	    && TREE_CODE (TREE_PURPOSE (t)) == TREE_VEC)
8120 	  {
8121 	    if (TREE_PURPOSE (t) != last_iter)
8122 	      {
8123 		if (last_bind)
8124 		  gimplify_and_add (last_bind, pre_p);
8125 		tree block = TREE_VEC_ELT (TREE_PURPOSE (t), 5);
8126 		last_bind = build3 (BIND_EXPR, void_type_node,
8127 				    BLOCK_VARS (block), NULL, block);
8128 		TREE_SIDE_EFFECTS (last_bind) = 1;
8129 		SET_EXPR_LOCATION (last_bind, OMP_CLAUSE_LOCATION (c));
8130 		tree *p = &BIND_EXPR_BODY (last_bind);
8131 		for (tree it = TREE_PURPOSE (t); it; it = TREE_CHAIN (it))
8132 		  {
8133 		    tree var = TREE_VEC_ELT (it, 0);
8134 		    tree begin = TREE_VEC_ELT (it, 1);
8135 		    tree end = TREE_VEC_ELT (it, 2);
8136 		    tree step = TREE_VEC_ELT (it, 3);
8137 		    tree orig_step = TREE_VEC_ELT (it, 4);
8138 		    tree type = TREE_TYPE (var);
8139 		    location_t loc = DECL_SOURCE_LOCATION (var);
8140 		    /* Emit:
8141 		       var = begin;
8142 		       goto cond_label;
8143 		       beg_label:
8144 		       ...
8145 		       var = var + step;
8146 		       cond_label:
8147 		       if (orig_step > 0) {
8148 			 if (var < end) goto beg_label;
8149 		       } else {
8150 			 if (var > end) goto beg_label;
8151 		       }
8152 		       for each iterator, with inner iterators added to
8153 		       the ... above.  */
8154 		    tree beg_label = create_artificial_label (loc);
8155 		    tree cond_label = NULL_TREE;
8156 		    tem = build2_loc (loc, MODIFY_EXPR, void_type_node,
8157 				      var, begin);
8158 		    append_to_statement_list_force (tem, p);
8159 		    tem = build_and_jump (&cond_label);
8160 		    append_to_statement_list_force (tem, p);
8161 		    tem = build1 (LABEL_EXPR, void_type_node, beg_label);
8162 		    append_to_statement_list (tem, p);
8163 		    tree bind = build3 (BIND_EXPR, void_type_node, NULL_TREE,
8164 					NULL_TREE, NULL_TREE);
8165 		    TREE_SIDE_EFFECTS (bind) = 1;
8166 		    SET_EXPR_LOCATION (bind, loc);
8167 		    append_to_statement_list_force (bind, p);
8168 		    if (POINTER_TYPE_P (type))
8169 		      tem = build2_loc (loc, POINTER_PLUS_EXPR, type,
8170 					var, fold_convert_loc (loc, sizetype,
8171 							       step));
8172 		    else
8173 		      tem = build2_loc (loc, PLUS_EXPR, type, var, step);
8174 		    tem = build2_loc (loc, MODIFY_EXPR, void_type_node,
8175 				      var, tem);
8176 		    append_to_statement_list_force (tem, p);
8177 		    tem = build1 (LABEL_EXPR, void_type_node, cond_label);
8178 		    append_to_statement_list (tem, p);
8179 		    tree cond = fold_build2_loc (loc, LT_EXPR,
8180 						 boolean_type_node,
8181 						 var, end);
8182 		    tree pos
8183 		      = fold_build3_loc (loc, COND_EXPR, void_type_node,
8184 					 cond, build_and_jump (&beg_label),
8185 					 void_node);
8186 		    cond = fold_build2_loc (loc, GT_EXPR, boolean_type_node,
8187 					    var, end);
8188 		    tree neg
8189 		      = fold_build3_loc (loc, COND_EXPR, void_type_node,
8190 					 cond, build_and_jump (&beg_label),
8191 					 void_node);
8192 		    tree osteptype = TREE_TYPE (orig_step);
8193 		    cond = fold_build2_loc (loc, GT_EXPR, boolean_type_node,
8194 					    orig_step,
8195 					    build_int_cst (osteptype, 0));
8196 		    tem = fold_build3_loc (loc, COND_EXPR, void_type_node,
8197 					   cond, pos, neg);
8198 		    append_to_statement_list_force (tem, p);
8199 		    p = &BIND_EXPR_BODY (bind);
8200 		  }
8201 		last_body = p;
8202 	      }
8203 	    last_iter = TREE_PURPOSE (t);
8204 	    if (TREE_CODE (TREE_VALUE (t)) == COMPOUND_EXPR)
8205 	      {
8206 		append_to_statement_list (TREE_OPERAND (TREE_VALUE (t),
8207 					  0), last_body);
8208 		TREE_VALUE (t) = TREE_OPERAND (TREE_VALUE (t), 1);
8209 	      }
8210 	    if (error_operand_p (TREE_VALUE (t)))
8211 	      return 2;
8212 	    TREE_VALUE (t) = build_fold_addr_expr (TREE_VALUE (t));
8213 	    r = build4 (ARRAY_REF, ptr_type_node, array, cnts[i],
8214 			NULL_TREE, NULL_TREE);
8215 	    tem = build2_loc (OMP_CLAUSE_LOCATION (c), MODIFY_EXPR,
8216 			      void_type_node, r, TREE_VALUE (t));
8217 	    append_to_statement_list_force (tem, last_body);
8218 	    tem = build2_loc (OMP_CLAUSE_LOCATION (c), MODIFY_EXPR,
8219 			      void_type_node, cnts[i],
8220 			      size_binop (PLUS_EXPR, cnts[i], size_int (1)));
8221 	    append_to_statement_list_force (tem, last_body);
8222 	    TREE_VALUE (t) = null_pointer_node;
8223 	  }
8224 	else
8225 	  {
8226 	    if (last_bind)
8227 	      {
8228 		gimplify_and_add (last_bind, pre_p);
8229 		last_bind = NULL_TREE;
8230 	      }
8231 	    if (TREE_CODE (OMP_CLAUSE_DECL (c)) == COMPOUND_EXPR)
8232 	      {
8233 		gimplify_expr (&TREE_OPERAND (OMP_CLAUSE_DECL (c), 0), pre_p,
8234 			       NULL, is_gimple_val, fb_rvalue);
8235 		OMP_CLAUSE_DECL (c) = TREE_OPERAND (OMP_CLAUSE_DECL (c), 1);
8236 	      }
8237 	    if (error_operand_p (OMP_CLAUSE_DECL (c)))
8238 	      return 2;
8239 	    OMP_CLAUSE_DECL (c) = build_fold_addr_expr (OMP_CLAUSE_DECL (c));
8240 	    if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p, NULL,
8241 			       is_gimple_val, fb_rvalue) == GS_ERROR)
8242 	      return 2;
8243 	    r = build4 (ARRAY_REF, ptr_type_node, array, cnts[i],
8244 			NULL_TREE, NULL_TREE);
8245 	    tem = build2 (MODIFY_EXPR, void_type_node, r, OMP_CLAUSE_DECL (c));
8246 	    gimplify_and_add (tem, pre_p);
8247 	    g = gimple_build_assign (cnts[i], size_binop (PLUS_EXPR, cnts[i],
8248 							  size_int (1)));
8249 	    gimple_seq_add_stmt (pre_p, g);
8250 	  }
8251       }
8252   if (last_bind)
8253     gimplify_and_add (last_bind, pre_p);
8254   tree cond = boolean_false_node;
8255   if (is_old)
8256     {
8257       if (!unused[0])
8258 	cond = build2_loc (first_loc, NE_EXPR, boolean_type_node, cnts[0],
8259 			   size_binop_loc (first_loc, PLUS_EXPR, counts[0],
8260 					   size_int (2)));
8261       if (!unused[2])
8262 	cond = build2_loc (first_loc, TRUTH_OR_EXPR, boolean_type_node, cond,
8263 			   build2_loc (first_loc, NE_EXPR, boolean_type_node,
8264 				       cnts[2],
8265 				       size_binop_loc (first_loc, PLUS_EXPR,
8266 						       totalpx,
8267 						       size_int (1))));
8268     }
8269   else
8270     {
8271       tree prev = size_int (5);
8272       for (i = 0; i < 4; i++)
8273 	{
8274 	  if (unused[i])
8275 	    continue;
8276 	  prev = size_binop_loc (first_loc, PLUS_EXPR, counts[i], prev);
8277 	  cond = build2_loc (first_loc, TRUTH_OR_EXPR, boolean_type_node, cond,
8278 			     build2_loc (first_loc, NE_EXPR, boolean_type_node,
8279 					 cnts[i], unshare_expr (prev)));
8280 	}
8281     }
8282   tem = build3_loc (first_loc, COND_EXPR, void_type_node, cond,
8283 		    build_call_expr_loc (first_loc,
8284 					 builtin_decl_explicit (BUILT_IN_TRAP),
8285 					 0), void_node);
8286   gimplify_and_add (tem, pre_p);
8287   c = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_DEPEND);
8288   OMP_CLAUSE_DEPEND_KIND (c) = OMP_CLAUSE_DEPEND_LAST;
8289   OMP_CLAUSE_DECL (c) = build_fold_addr_expr (array);
8290   OMP_CLAUSE_CHAIN (c) = *list_p;
8291   *list_p = c;
8292   return 1;
8293 }
8294 
8295 /* Insert a GOMP_MAP_ALLOC or GOMP_MAP_RELEASE node following a
8296    GOMP_MAP_STRUCT mapping.  C is an always_pointer mapping.  STRUCT_NODE is
8297    the struct node to insert the new mapping after (when the struct node is
8298    initially created).  PREV_NODE is the first of two or three mappings for a
8299    pointer, and is either:
8300      - the node before C, when a pair of mappings is used, e.g. for a C/C++
8301        array section.
8302      - not the node before C.  This is true when we have a reference-to-pointer
8303        type (with a mapping for the reference and for the pointer), or for
8304        Fortran derived-type mappings with a GOMP_MAP_TO_PSET.
8305    If SCP is non-null, the new node is inserted before *SCP.
8306    if SCP is null, the new node is inserted before PREV_NODE.
8307    The return type is:
8308      - PREV_NODE, if SCP is non-null.
8309      - The newly-created ALLOC or RELEASE node, if SCP is null.
8310      - The second newly-created ALLOC or RELEASE node, if we are mapping a
8311        reference to a pointer.  */
8312 
8313 static tree
insert_struct_comp_map(enum tree_code code,tree c,tree struct_node,tree prev_node,tree * scp)8314 insert_struct_comp_map (enum tree_code code, tree c, tree struct_node,
8315 			tree prev_node, tree *scp)
8316 {
8317   enum gomp_map_kind mkind
8318     = (code == OMP_TARGET_EXIT_DATA || code == OACC_EXIT_DATA)
8319       ? GOMP_MAP_RELEASE : GOMP_MAP_ALLOC;
8320 
8321   tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_MAP);
8322   tree cl = scp ? prev_node : c2;
8323   OMP_CLAUSE_SET_MAP_KIND (c2, mkind);
8324   OMP_CLAUSE_DECL (c2) = unshare_expr (OMP_CLAUSE_DECL (c));
8325   OMP_CLAUSE_CHAIN (c2) = scp ? *scp : prev_node;
8326   if (OMP_CLAUSE_CHAIN (prev_node) != c
8327       && OMP_CLAUSE_CODE (OMP_CLAUSE_CHAIN (prev_node)) == OMP_CLAUSE_MAP
8328       && (OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (prev_node))
8329 	  == GOMP_MAP_TO_PSET))
8330     OMP_CLAUSE_SIZE (c2) = OMP_CLAUSE_SIZE (OMP_CLAUSE_CHAIN (prev_node));
8331   else
8332     OMP_CLAUSE_SIZE (c2) = TYPE_SIZE_UNIT (ptr_type_node);
8333   if (struct_node)
8334     OMP_CLAUSE_CHAIN (struct_node) = c2;
8335 
8336   /* We might need to create an additional mapping if we have a reference to a
8337      pointer (in C++).  Don't do this if we have something other than a
8338      GOMP_MAP_ALWAYS_POINTER though, i.e. a GOMP_MAP_TO_PSET.  */
8339   if (OMP_CLAUSE_CHAIN (prev_node) != c
8340       && OMP_CLAUSE_CODE (OMP_CLAUSE_CHAIN (prev_node)) == OMP_CLAUSE_MAP
8341       && ((OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (prev_node))
8342 	   == GOMP_MAP_ALWAYS_POINTER)
8343 	  || (OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (prev_node))
8344 	      == GOMP_MAP_ATTACH_DETACH)))
8345     {
8346       tree c4 = OMP_CLAUSE_CHAIN (prev_node);
8347       tree c3 = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_MAP);
8348       OMP_CLAUSE_SET_MAP_KIND (c3, mkind);
8349       OMP_CLAUSE_DECL (c3) = unshare_expr (OMP_CLAUSE_DECL (c4));
8350       OMP_CLAUSE_SIZE (c3) = TYPE_SIZE_UNIT (ptr_type_node);
8351       OMP_CLAUSE_CHAIN (c3) = prev_node;
8352       if (!scp)
8353 	OMP_CLAUSE_CHAIN (c2) = c3;
8354       else
8355 	cl = c3;
8356     }
8357 
8358   if (scp)
8359     *scp = c2;
8360 
8361   return cl;
8362 }
8363 
8364 /* Strip ARRAY_REFS or an indirect ref off BASE, find the containing object,
8365    and set *BITPOSP and *POFFSETP to the bit offset of the access.
8366    If BASE_REF is non-NULL and the containing object is a reference, set
8367    *BASE_REF to that reference before dereferencing the object.
8368    If BASE_REF is NULL, check that the containing object is a COMPONENT_REF or
8369    has array type, else return NULL.  */
8370 
8371 static tree
extract_base_bit_offset(tree base,tree * base_ref,poly_int64 * bitposp,poly_offset_int * poffsetp)8372 extract_base_bit_offset (tree base, tree *base_ref, poly_int64 *bitposp,
8373 			 poly_offset_int *poffsetp)
8374 {
8375   tree offset;
8376   poly_int64 bitsize, bitpos;
8377   machine_mode mode;
8378   int unsignedp, reversep, volatilep = 0;
8379   poly_offset_int poffset;
8380 
8381   if (base_ref)
8382     {
8383       *base_ref = NULL_TREE;
8384 
8385       while (TREE_CODE (base) == ARRAY_REF)
8386 	base = TREE_OPERAND (base, 0);
8387 
8388       if (TREE_CODE (base) == INDIRECT_REF)
8389 	base = TREE_OPERAND (base, 0);
8390     }
8391   else
8392     {
8393       if (TREE_CODE (base) == ARRAY_REF)
8394 	{
8395 	  while (TREE_CODE (base) == ARRAY_REF)
8396 	    base = TREE_OPERAND (base, 0);
8397 	  if (TREE_CODE (base) != COMPONENT_REF
8398 	      || TREE_CODE (TREE_TYPE (base)) != ARRAY_TYPE)
8399 	    return NULL_TREE;
8400 	}
8401       else if (TREE_CODE (base) == INDIRECT_REF
8402 	       && TREE_CODE (TREE_OPERAND (base, 0)) == COMPONENT_REF
8403 	       && (TREE_CODE (TREE_TYPE (TREE_OPERAND (base, 0)))
8404 		   == REFERENCE_TYPE))
8405 	base = TREE_OPERAND (base, 0);
8406     }
8407 
8408   base = get_inner_reference (base, &bitsize, &bitpos, &offset, &mode,
8409 			      &unsignedp, &reversep, &volatilep);
8410 
8411   tree orig_base = base;
8412 
8413   if ((TREE_CODE (base) == INDIRECT_REF
8414        || (TREE_CODE (base) == MEM_REF
8415 	   && integer_zerop (TREE_OPERAND (base, 1))))
8416       && DECL_P (TREE_OPERAND (base, 0))
8417       && TREE_CODE (TREE_TYPE (TREE_OPERAND (base, 0))) == REFERENCE_TYPE)
8418     base = TREE_OPERAND (base, 0);
8419 
8420   gcc_assert (offset == NULL_TREE || poly_int_tree_p (offset));
8421 
8422   if (offset)
8423     poffset = wi::to_poly_offset (offset);
8424   else
8425     poffset = 0;
8426 
8427   if (maybe_ne (bitpos, 0))
8428     poffset += bits_to_bytes_round_down (bitpos);
8429 
8430   *bitposp = bitpos;
8431   *poffsetp = poffset;
8432 
8433   /* Set *BASE_REF if BASE was a dereferenced reference variable.  */
8434   if (base_ref && orig_base != base)
8435     *base_ref = orig_base;
8436 
8437   return base;
8438 }
8439 
8440 /* Returns true if EXPR is or contains (as a sub-component) BASE_PTR.  */
8441 
8442 static bool
is_or_contains_p(tree expr,tree base_ptr)8443 is_or_contains_p (tree expr, tree base_ptr)
8444 {
8445   while (expr != base_ptr)
8446     if (TREE_CODE (base_ptr) == COMPONENT_REF)
8447       base_ptr = TREE_OPERAND (base_ptr, 0);
8448     else
8449       break;
8450   return expr == base_ptr;
8451 }
8452 
8453 /* Implement OpenMP 5.x map ordering rules for target directives. There are
8454    several rules, and with some level of ambiguity, hopefully we can at least
8455    collect the complexity here in one place.  */
8456 
8457 static void
omp_target_reorder_clauses(tree * list_p)8458 omp_target_reorder_clauses (tree *list_p)
8459 {
8460   /* Collect refs to alloc/release/delete maps.  */
8461   auto_vec<tree, 32> ard;
8462   tree *cp = list_p;
8463   while (*cp != NULL_TREE)
8464     if (OMP_CLAUSE_CODE (*cp) == OMP_CLAUSE_MAP
8465 	&& (OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_ALLOC
8466 	    || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_RELEASE
8467 	    || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_DELETE))
8468       {
8469 	/* Unlink cp and push to ard.  */
8470 	tree c = *cp;
8471 	tree nc = OMP_CLAUSE_CHAIN (c);
8472 	*cp = nc;
8473 	ard.safe_push (c);
8474 
8475 	/* Any associated pointer type maps should also move along.  */
8476 	while (*cp != NULL_TREE
8477 	       && OMP_CLAUSE_CODE (*cp) == OMP_CLAUSE_MAP
8478 	       && (OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_FIRSTPRIVATE_REFERENCE
8479 		   || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_FIRSTPRIVATE_POINTER
8480 		   || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_ATTACH_DETACH
8481 		   || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_POINTER
8482 		   || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_ALWAYS_POINTER
8483 		   || OMP_CLAUSE_MAP_KIND (*cp) == GOMP_MAP_TO_PSET))
8484 	  {
8485 	    c = *cp;
8486 	    nc = OMP_CLAUSE_CHAIN (c);
8487 	    *cp = nc;
8488 	    ard.safe_push (c);
8489 	  }
8490       }
8491     else
8492       cp = &OMP_CLAUSE_CHAIN (*cp);
8493 
8494   /* Link alloc/release/delete maps to the end of list.  */
8495   for (unsigned int i = 0; i < ard.length (); i++)
8496     {
8497       *cp = ard[i];
8498       cp = &OMP_CLAUSE_CHAIN (ard[i]);
8499     }
8500   *cp = NULL_TREE;
8501 
8502   /* OpenMP 5.0 requires that pointer variables are mapped before
8503      its use as a base-pointer.  */
8504   auto_vec<tree *, 32> atf;
8505   for (tree *cp = list_p; *cp; cp = &OMP_CLAUSE_CHAIN (*cp))
8506     if (OMP_CLAUSE_CODE (*cp) == OMP_CLAUSE_MAP)
8507       {
8508 	/* Collect alloc, to, from, to/from clause tree pointers.  */
8509 	gomp_map_kind k = OMP_CLAUSE_MAP_KIND (*cp);
8510 	if (k == GOMP_MAP_ALLOC
8511 	    || k == GOMP_MAP_TO
8512 	    || k == GOMP_MAP_FROM
8513 	    || k == GOMP_MAP_TOFROM
8514 	    || k == GOMP_MAP_ALWAYS_TO
8515 	    || k == GOMP_MAP_ALWAYS_FROM
8516 	    || k == GOMP_MAP_ALWAYS_TOFROM)
8517 	  atf.safe_push (cp);
8518       }
8519 
8520   for (unsigned int i = 0; i < atf.length (); i++)
8521     if (atf[i])
8522       {
8523 	tree *cp = atf[i];
8524 	tree decl = OMP_CLAUSE_DECL (*cp);
8525 	if (TREE_CODE (decl) == INDIRECT_REF || TREE_CODE (decl) == MEM_REF)
8526 	  {
8527 	    tree base_ptr = TREE_OPERAND (decl, 0);
8528 	    STRIP_TYPE_NOPS (base_ptr);
8529 	    for (unsigned int j = i + 1; j < atf.length (); j++)
8530 	      {
8531 		tree *cp2 = atf[j];
8532 		tree decl2 = OMP_CLAUSE_DECL (*cp2);
8533 		if (is_or_contains_p (decl2, base_ptr))
8534 		  {
8535 		    /* Move *cp2 to before *cp.  */
8536 		    tree c = *cp2;
8537 		    *cp2 = OMP_CLAUSE_CHAIN (c);
8538 		    OMP_CLAUSE_CHAIN (c) = *cp;
8539 		    *cp = c;
8540 		    atf[j] = NULL;
8541 		  }
8542 	      }
8543 	  }
8544       }
8545 }
8546 
8547 /* Scan the OMP clauses in *LIST_P, installing mappings into a new
8548    and previous omp contexts.  */
8549 
8550 static void
gimplify_scan_omp_clauses(tree * list_p,gimple_seq * pre_p,enum omp_region_type region_type,enum tree_code code)8551 gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
8552 			   enum omp_region_type region_type,
8553 			   enum tree_code code)
8554 {
8555   struct gimplify_omp_ctx *ctx, *outer_ctx;
8556   tree c;
8557   hash_map<tree, tree> *struct_map_to_clause = NULL;
8558   hash_set<tree> *struct_deref_set = NULL;
8559   tree *prev_list_p = NULL, *orig_list_p = list_p;
8560   int handled_depend_iterators = -1;
8561   int nowait = -1;
8562 
8563   ctx = new_omp_context (region_type);
8564   ctx->code = code;
8565   outer_ctx = ctx->outer_context;
8566   if (code == OMP_TARGET)
8567     {
8568       if (!lang_GNU_Fortran ())
8569 	ctx->defaultmap[GDMK_POINTER] = GOVD_MAP | GOVD_MAP_0LEN_ARRAY;
8570       ctx->defaultmap[GDMK_SCALAR] = GOVD_FIRSTPRIVATE;
8571     }
8572   if (!lang_GNU_Fortran ())
8573     switch (code)
8574       {
8575       case OMP_TARGET:
8576       case OMP_TARGET_DATA:
8577       case OMP_TARGET_ENTER_DATA:
8578       case OMP_TARGET_EXIT_DATA:
8579       case OACC_DECLARE:
8580       case OACC_HOST_DATA:
8581       case OACC_PARALLEL:
8582       case OACC_KERNELS:
8583 	ctx->target_firstprivatize_array_bases = true;
8584       default:
8585 	break;
8586       }
8587 
8588   if (code == OMP_TARGET
8589       || code == OMP_TARGET_DATA
8590       || code == OMP_TARGET_ENTER_DATA
8591       || code == OMP_TARGET_EXIT_DATA)
8592     omp_target_reorder_clauses (list_p);
8593 
8594   while ((c = *list_p) != NULL)
8595     {
8596       bool remove = false;
8597       bool notice_outer = true;
8598       const char *check_non_private = NULL;
8599       unsigned int flags;
8600       tree decl;
8601 
8602       switch (OMP_CLAUSE_CODE (c))
8603 	{
8604 	case OMP_CLAUSE_PRIVATE:
8605 	  flags = GOVD_PRIVATE | GOVD_EXPLICIT;
8606 	  if (lang_hooks.decls.omp_private_outer_ref (OMP_CLAUSE_DECL (c)))
8607 	    {
8608 	      flags |= GOVD_PRIVATE_OUTER_REF;
8609 	      OMP_CLAUSE_PRIVATE_OUTER_REF (c) = 1;
8610 	    }
8611 	  else
8612 	    notice_outer = false;
8613 	  goto do_add;
8614 	case OMP_CLAUSE_SHARED:
8615 	  flags = GOVD_SHARED | GOVD_EXPLICIT;
8616 	  goto do_add;
8617 	case OMP_CLAUSE_FIRSTPRIVATE:
8618 	  flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
8619 	  check_non_private = "firstprivate";
8620 	  goto do_add;
8621 	case OMP_CLAUSE_LASTPRIVATE:
8622 	  if (OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c))
8623 	    switch (code)
8624 	      {
8625 	      case OMP_DISTRIBUTE:
8626 		error_at (OMP_CLAUSE_LOCATION (c),
8627 			  "conditional %<lastprivate%> clause on "
8628 			  "%qs construct", "distribute");
8629 		OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 0;
8630 		break;
8631 	      case OMP_TASKLOOP:
8632 		error_at (OMP_CLAUSE_LOCATION (c),
8633 			  "conditional %<lastprivate%> clause on "
8634 			  "%qs construct", "taskloop");
8635 		OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 0;
8636 		break;
8637 	      default:
8638 		break;
8639 	      }
8640 	  flags = GOVD_LASTPRIVATE | GOVD_SEEN | GOVD_EXPLICIT;
8641 	  if (code != OMP_LOOP)
8642 	    check_non_private = "lastprivate";
8643 	  decl = OMP_CLAUSE_DECL (c);
8644 	  if (error_operand_p (decl))
8645 	    goto do_add;
8646 	  if (OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c)
8647 	      && !lang_hooks.decls.omp_scalar_p (decl))
8648 	    {
8649 	      error_at (OMP_CLAUSE_LOCATION (c),
8650 			"non-scalar variable %qD in conditional "
8651 			"%<lastprivate%> clause", decl);
8652 	      OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 0;
8653 	    }
8654 	  if (OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c))
8655 	    flags |= GOVD_LASTPRIVATE_CONDITIONAL;
8656 	  if (outer_ctx
8657 	      && (outer_ctx->region_type == ORT_COMBINED_PARALLEL
8658 		  || ((outer_ctx->region_type & ORT_COMBINED_TEAMS)
8659 		      == ORT_COMBINED_TEAMS))
8660 	      && splay_tree_lookup (outer_ctx->variables,
8661 				    (splay_tree_key) decl) == NULL)
8662 	    {
8663 	      omp_add_variable (outer_ctx, decl, GOVD_SHARED | GOVD_SEEN);
8664 	      if (outer_ctx->outer_context)
8665 		omp_notice_variable (outer_ctx->outer_context, decl, true);
8666 	    }
8667 	  else if (outer_ctx
8668 		   && (outer_ctx->region_type & ORT_TASK) != 0
8669 		   && outer_ctx->combined_loop
8670 		   && splay_tree_lookup (outer_ctx->variables,
8671 					 (splay_tree_key) decl) == NULL)
8672 	    {
8673 	      omp_add_variable (outer_ctx, decl, GOVD_LASTPRIVATE | GOVD_SEEN);
8674 	      if (outer_ctx->outer_context)
8675 		omp_notice_variable (outer_ctx->outer_context, decl, true);
8676 	    }
8677 	  else if (outer_ctx
8678 		   && (outer_ctx->region_type == ORT_WORKSHARE
8679 		       || outer_ctx->region_type == ORT_ACC)
8680 		   && outer_ctx->combined_loop
8681 		   && splay_tree_lookup (outer_ctx->variables,
8682 					 (splay_tree_key) decl) == NULL
8683 		   && !omp_check_private (outer_ctx, decl, false))
8684 	    {
8685 	      omp_add_variable (outer_ctx, decl, GOVD_LASTPRIVATE | GOVD_SEEN);
8686 	      if (outer_ctx->outer_context
8687 		  && (outer_ctx->outer_context->region_type
8688 		      == ORT_COMBINED_PARALLEL)
8689 		  && splay_tree_lookup (outer_ctx->outer_context->variables,
8690 					(splay_tree_key) decl) == NULL)
8691 		{
8692 		  struct gimplify_omp_ctx *octx = outer_ctx->outer_context;
8693 		  omp_add_variable (octx, decl, GOVD_SHARED | GOVD_SEEN);
8694 		  if (octx->outer_context)
8695 		    {
8696 		      octx = octx->outer_context;
8697 		      if (octx->region_type == ORT_WORKSHARE
8698 			  && octx->combined_loop
8699 			  && splay_tree_lookup (octx->variables,
8700 						(splay_tree_key) decl) == NULL
8701 			  && !omp_check_private (octx, decl, false))
8702 			{
8703 			  omp_add_variable (octx, decl,
8704 					    GOVD_LASTPRIVATE | GOVD_SEEN);
8705 			  octx = octx->outer_context;
8706 			  if (octx
8707 			      && ((octx->region_type & ORT_COMBINED_TEAMS)
8708 				  == ORT_COMBINED_TEAMS)
8709 			      && (splay_tree_lookup (octx->variables,
8710 						     (splay_tree_key) decl)
8711 				  == NULL))
8712 			    {
8713 			      omp_add_variable (octx, decl,
8714 						GOVD_SHARED | GOVD_SEEN);
8715 			      octx = octx->outer_context;
8716 			    }
8717 			}
8718 		      if (octx)
8719 			omp_notice_variable (octx, decl, true);
8720 		    }
8721 		}
8722 	      else if (outer_ctx->outer_context)
8723 		omp_notice_variable (outer_ctx->outer_context, decl, true);
8724 	    }
8725 	  goto do_add;
8726 	case OMP_CLAUSE_REDUCTION:
8727 	  if (OMP_CLAUSE_REDUCTION_TASK (c))
8728 	    {
8729 	      if (region_type == ORT_WORKSHARE)
8730 		{
8731 		  if (nowait == -1)
8732 		    nowait = omp_find_clause (*list_p,
8733 					      OMP_CLAUSE_NOWAIT) != NULL_TREE;
8734 		  if (nowait
8735 		      && (outer_ctx == NULL
8736 			  || outer_ctx->region_type != ORT_COMBINED_PARALLEL))
8737 		    {
8738 		      error_at (OMP_CLAUSE_LOCATION (c),
8739 				"%<task%> reduction modifier on a construct "
8740 				"with a %<nowait%> clause");
8741 		      OMP_CLAUSE_REDUCTION_TASK (c) = 0;
8742 		    }
8743 		}
8744 	      else if ((region_type & ORT_PARALLEL) != ORT_PARALLEL)
8745 		{
8746 		  error_at (OMP_CLAUSE_LOCATION (c),
8747 			    "invalid %<task%> reduction modifier on construct "
8748 			    "other than %<parallel%>, %qs or %<sections%>",
8749 			    lang_GNU_Fortran () ? "do" : "for");
8750 		  OMP_CLAUSE_REDUCTION_TASK (c) = 0;
8751 		}
8752 	    }
8753 	  if (OMP_CLAUSE_REDUCTION_INSCAN (c))
8754 	    switch (code)
8755 	      {
8756 	      case OMP_SECTIONS:
8757 		error_at (OMP_CLAUSE_LOCATION (c),
8758 			  "%<inscan%> %<reduction%> clause on "
8759 			  "%qs construct", "sections");
8760 		OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
8761 		break;
8762 	      case OMP_PARALLEL:
8763 		error_at (OMP_CLAUSE_LOCATION (c),
8764 			  "%<inscan%> %<reduction%> clause on "
8765 			  "%qs construct", "parallel");
8766 		OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
8767 		break;
8768 	      case OMP_TEAMS:
8769 		error_at (OMP_CLAUSE_LOCATION (c),
8770 			  "%<inscan%> %<reduction%> clause on "
8771 			  "%qs construct", "teams");
8772 		OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
8773 		break;
8774 	      case OMP_TASKLOOP:
8775 		error_at (OMP_CLAUSE_LOCATION (c),
8776 			  "%<inscan%> %<reduction%> clause on "
8777 			  "%qs construct", "taskloop");
8778 		OMP_CLAUSE_REDUCTION_INSCAN (c) = 0;
8779 		break;
8780 	      default:
8781 		break;
8782 	      }
8783 	  /* FALLTHRU */
8784 	case OMP_CLAUSE_IN_REDUCTION:
8785 	case OMP_CLAUSE_TASK_REDUCTION:
8786 	  flags = GOVD_REDUCTION | GOVD_SEEN | GOVD_EXPLICIT;
8787 	  /* OpenACC permits reductions on private variables.  */
8788 	  if (!(region_type & ORT_ACC)
8789 	      /* taskgroup is actually not a worksharing region.  */
8790 	      && code != OMP_TASKGROUP)
8791 	    check_non_private = omp_clause_code_name[OMP_CLAUSE_CODE (c)];
8792 	  decl = OMP_CLAUSE_DECL (c);
8793 	  if (TREE_CODE (decl) == MEM_REF)
8794 	    {
8795 	      tree type = TREE_TYPE (decl);
8796 	      bool saved_into_ssa = gimplify_ctxp->into_ssa;
8797 	      gimplify_ctxp->into_ssa = false;
8798 	      if (gimplify_expr (&TYPE_MAX_VALUE (TYPE_DOMAIN (type)), pre_p,
8799 				 NULL, is_gimple_val, fb_rvalue, false)
8800 		  == GS_ERROR)
8801 		{
8802 		  gimplify_ctxp->into_ssa = saved_into_ssa;
8803 		  remove = true;
8804 		  break;
8805 		}
8806 	      gimplify_ctxp->into_ssa = saved_into_ssa;
8807 	      tree v = TYPE_MAX_VALUE (TYPE_DOMAIN (type));
8808 	      if (DECL_P (v))
8809 		{
8810 		  omp_firstprivatize_variable (ctx, v);
8811 		  omp_notice_variable (ctx, v, true);
8812 		}
8813 	      decl = TREE_OPERAND (decl, 0);
8814 	      if (TREE_CODE (decl) == POINTER_PLUS_EXPR)
8815 		{
8816 		  gimplify_ctxp->into_ssa = false;
8817 		  if (gimplify_expr (&TREE_OPERAND (decl, 1), pre_p,
8818 				     NULL, is_gimple_val, fb_rvalue, false)
8819 		      == GS_ERROR)
8820 		    {
8821 		      gimplify_ctxp->into_ssa = saved_into_ssa;
8822 		      remove = true;
8823 		      break;
8824 		    }
8825 		  gimplify_ctxp->into_ssa = saved_into_ssa;
8826 		  v = TREE_OPERAND (decl, 1);
8827 		  if (DECL_P (v))
8828 		    {
8829 		      omp_firstprivatize_variable (ctx, v);
8830 		      omp_notice_variable (ctx, v, true);
8831 		    }
8832 		  decl = TREE_OPERAND (decl, 0);
8833 		}
8834 	      if (TREE_CODE (decl) == ADDR_EXPR
8835 		  || TREE_CODE (decl) == INDIRECT_REF)
8836 		decl = TREE_OPERAND (decl, 0);
8837 	    }
8838 	  goto do_add_decl;
8839 	case OMP_CLAUSE_LINEAR:
8840 	  if (gimplify_expr (&OMP_CLAUSE_LINEAR_STEP (c), pre_p, NULL,
8841 			     is_gimple_val, fb_rvalue) == GS_ERROR)
8842 	    {
8843 	      remove = true;
8844 	      break;
8845 	    }
8846 	  else
8847 	    {
8848 	      if (code == OMP_SIMD
8849 		  && !OMP_CLAUSE_LINEAR_NO_COPYIN (c))
8850 		{
8851 		  struct gimplify_omp_ctx *octx = outer_ctx;
8852 		  if (octx
8853 		      && octx->region_type == ORT_WORKSHARE
8854 		      && octx->combined_loop
8855 		      && !octx->distribute)
8856 		    {
8857 		      if (octx->outer_context
8858 			  && (octx->outer_context->region_type
8859 			      == ORT_COMBINED_PARALLEL))
8860 			octx = octx->outer_context->outer_context;
8861 		      else
8862 			octx = octx->outer_context;
8863 		    }
8864 		  if (octx
8865 		      && octx->region_type == ORT_WORKSHARE
8866 		      && octx->combined_loop
8867 		      && octx->distribute)
8868 		    {
8869 		      error_at (OMP_CLAUSE_LOCATION (c),
8870 				"%<linear%> clause for variable other than "
8871 				"loop iterator specified on construct "
8872 				"combined with %<distribute%>");
8873 		      remove = true;
8874 		      break;
8875 		    }
8876 		}
8877 	      /* For combined #pragma omp parallel for simd, need to put
8878 		 lastprivate and perhaps firstprivate too on the
8879 		 parallel.  Similarly for #pragma omp for simd.  */
8880 	      struct gimplify_omp_ctx *octx = outer_ctx;
8881 	      decl = NULL_TREE;
8882 	      do
8883 		{
8884 		  if (OMP_CLAUSE_LINEAR_NO_COPYIN (c)
8885 		      && OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
8886 		    break;
8887 		  decl = OMP_CLAUSE_DECL (c);
8888 		  if (error_operand_p (decl))
8889 		    {
8890 		      decl = NULL_TREE;
8891 		      break;
8892 		    }
8893 		  flags = GOVD_SEEN;
8894 		  if (!OMP_CLAUSE_LINEAR_NO_COPYIN (c))
8895 		    flags |= GOVD_FIRSTPRIVATE;
8896 		  if (!OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
8897 		    flags |= GOVD_LASTPRIVATE;
8898 		  if (octx
8899 		      && octx->region_type == ORT_WORKSHARE
8900 		      && octx->combined_loop)
8901 		    {
8902 		      if (octx->outer_context
8903 			  && (octx->outer_context->region_type
8904 			      == ORT_COMBINED_PARALLEL))
8905 			octx = octx->outer_context;
8906 		      else if (omp_check_private (octx, decl, false))
8907 			break;
8908 		    }
8909 		  else if (octx
8910 			   && (octx->region_type & ORT_TASK) != 0
8911 			   && octx->combined_loop)
8912 		    ;
8913 		  else if (octx
8914 			   && octx->region_type == ORT_COMBINED_PARALLEL
8915 			   && ctx->region_type == ORT_WORKSHARE
8916 			   && octx == outer_ctx)
8917 		    flags = GOVD_SEEN | GOVD_SHARED;
8918 		  else if (octx
8919 			   && ((octx->region_type & ORT_COMBINED_TEAMS)
8920 			       == ORT_COMBINED_TEAMS))
8921 		    flags = GOVD_SEEN | GOVD_SHARED;
8922 		  else if (octx
8923 			   && octx->region_type == ORT_COMBINED_TARGET)
8924 		    {
8925 		      flags &= ~GOVD_LASTPRIVATE;
8926 		      if (flags == GOVD_SEEN)
8927 			break;
8928 		    }
8929 		  else
8930 		    break;
8931 		  splay_tree_node on
8932 		    = splay_tree_lookup (octx->variables,
8933 					 (splay_tree_key) decl);
8934 		  if (on && (on->value & GOVD_DATA_SHARE_CLASS) != 0)
8935 		    {
8936 		      octx = NULL;
8937 		      break;
8938 		    }
8939 		  omp_add_variable (octx, decl, flags);
8940 		  if (octx->outer_context == NULL)
8941 		    break;
8942 		  octx = octx->outer_context;
8943 		}
8944 	      while (1);
8945 	      if (octx
8946 		  && decl
8947 		  && (!OMP_CLAUSE_LINEAR_NO_COPYIN (c)
8948 		      || !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)))
8949 		omp_notice_variable (octx, decl, true);
8950 	    }
8951 	  flags = GOVD_LINEAR | GOVD_EXPLICIT;
8952 	  if (OMP_CLAUSE_LINEAR_NO_COPYIN (c)
8953 	      && OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
8954 	    {
8955 	      notice_outer = false;
8956 	      flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
8957 	    }
8958 	  goto do_add;
8959 
8960 	case OMP_CLAUSE_MAP:
8961 	  decl = OMP_CLAUSE_DECL (c);
8962 	  if (error_operand_p (decl))
8963 	    remove = true;
8964 	  switch (code)
8965 	    {
8966 	    case OMP_TARGET:
8967 	      break;
8968 	    case OACC_DATA:
8969 	      if (TREE_CODE (TREE_TYPE (decl)) != ARRAY_TYPE)
8970 		break;
8971 	      /* FALLTHRU */
8972 	    case OMP_TARGET_DATA:
8973 	    case OMP_TARGET_ENTER_DATA:
8974 	    case OMP_TARGET_EXIT_DATA:
8975 	    case OACC_ENTER_DATA:
8976 	    case OACC_EXIT_DATA:
8977 	    case OACC_HOST_DATA:
8978 	      if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
8979 		  || (OMP_CLAUSE_MAP_KIND (c)
8980 		      == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
8981 		/* For target {,enter ,exit }data only the array slice is
8982 		   mapped, but not the pointer to it.  */
8983 		remove = true;
8984 	      break;
8985 	    default:
8986 	      break;
8987 	    }
8988 	  /* For Fortran, not only the pointer to the data is mapped but also
8989 	     the address of the pointer, the array descriptor etc.; for
8990 	     'exit data' - and in particular for 'delete:' - having an 'alloc:'
8991 	     does not make sense.  Likewise, for 'update' only transferring the
8992 	     data itself is needed as the rest has been handled in previous
8993 	     directives.  However, for 'exit data', the array descriptor needs
8994 	     to be delete; hence, we turn the MAP_TO_PSET into a MAP_DELETE.
8995 
8996 	     NOTE: Generally, it is not safe to perform "enter data" operations
8997 	     on arrays where the data *or the descriptor* may go out of scope
8998 	     before a corresponding "exit data" operation -- and such a
8999 	     descriptor may be synthesized temporarily, e.g. to pass an
9000 	     explicit-shape array to a function expecting an assumed-shape
9001 	     argument.  Performing "enter data" inside the called function
9002 	     would thus be problematic.  */
9003 	  if (code == OMP_TARGET_EXIT_DATA
9004 	      && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_TO_PSET)
9005 	    OMP_CLAUSE_SET_MAP_KIND (c, OMP_CLAUSE_MAP_KIND (*prev_list_p)
9006 					== GOMP_MAP_DELETE
9007 					? GOMP_MAP_DELETE : GOMP_MAP_RELEASE);
9008 	  else if ((code == OMP_TARGET_EXIT_DATA || code == OMP_TARGET_UPDATE)
9009 		   && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_POINTER
9010 		       || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_TO_PSET))
9011 	    remove = true;
9012 
9013 	  if (remove)
9014 	    break;
9015 	  if (DECL_P (decl) && outer_ctx && (region_type & ORT_ACC))
9016 	    {
9017 	      struct gimplify_omp_ctx *octx;
9018 	      for (octx = outer_ctx; octx; octx = octx->outer_context)
9019 	        {
9020 		  if (octx->region_type != ORT_ACC_HOST_DATA)
9021 		    break;
9022 		  splay_tree_node n2
9023 		    = splay_tree_lookup (octx->variables,
9024 					 (splay_tree_key) decl);
9025 		  if (n2)
9026 		    error_at (OMP_CLAUSE_LOCATION (c), "variable %qE "
9027 			      "declared in enclosing %<host_data%> region",
9028 			      DECL_NAME (decl));
9029 		}
9030 	    }
9031 	  if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
9032 	    OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
9033 				  : TYPE_SIZE_UNIT (TREE_TYPE (decl));
9034 	  if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
9035 			     NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
9036 	    {
9037 	      remove = true;
9038 	      break;
9039 	    }
9040 	  else if ((OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
9041 		    || (OMP_CLAUSE_MAP_KIND (c)
9042 			== GOMP_MAP_FIRSTPRIVATE_REFERENCE)
9043 		    || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH)
9044 		   && TREE_CODE (OMP_CLAUSE_SIZE (c)) != INTEGER_CST)
9045 	    {
9046 	      OMP_CLAUSE_SIZE (c)
9047 		= get_initialized_tmp_var (OMP_CLAUSE_SIZE (c), pre_p, NULL,
9048 					   false);
9049 	      if ((region_type & ORT_TARGET) != 0)
9050 		omp_add_variable (ctx, OMP_CLAUSE_SIZE (c),
9051 				  GOVD_FIRSTPRIVATE | GOVD_SEEN);
9052 	    }
9053 
9054 	  if (!DECL_P (decl))
9055 	    {
9056 	      tree d = decl, *pd;
9057 	      if (TREE_CODE (d) == ARRAY_REF)
9058 		{
9059 		  while (TREE_CODE (d) == ARRAY_REF)
9060 		    d = TREE_OPERAND (d, 0);
9061 		  if (TREE_CODE (d) == COMPONENT_REF
9062 		      && TREE_CODE (TREE_TYPE (d)) == ARRAY_TYPE)
9063 		    decl = d;
9064 		}
9065 	      pd = &OMP_CLAUSE_DECL (c);
9066 	      if (d == decl
9067 		  && TREE_CODE (decl) == INDIRECT_REF
9068 		  && TREE_CODE (TREE_OPERAND (decl, 0)) == COMPONENT_REF
9069 		  && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
9070 		      == REFERENCE_TYPE))
9071 		{
9072 		  pd = &TREE_OPERAND (decl, 0);
9073 		  decl = TREE_OPERAND (decl, 0);
9074 		}
9075 	      bool indir_p = false;
9076 	      tree orig_decl = decl;
9077 	      tree decl_ref = NULL_TREE;
9078 	      if ((region_type & (ORT_ACC | ORT_TARGET | ORT_TARGET_DATA)) != 0
9079 		  && TREE_CODE (*pd) == COMPONENT_REF
9080 		  && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH
9081 		  && code != OACC_UPDATE)
9082 		{
9083 		  while (TREE_CODE (decl) == COMPONENT_REF)
9084 		    {
9085 		      decl = TREE_OPERAND (decl, 0);
9086 		      if (((TREE_CODE (decl) == MEM_REF
9087 			    && integer_zerop (TREE_OPERAND (decl, 1)))
9088 			   || INDIRECT_REF_P (decl))
9089 			  && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
9090 			      == POINTER_TYPE))
9091 			{
9092 			  indir_p = true;
9093 			  decl = TREE_OPERAND (decl, 0);
9094 			}
9095 		      if (TREE_CODE (decl) == INDIRECT_REF
9096 			  && DECL_P (TREE_OPERAND (decl, 0))
9097 			  && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
9098 			      == REFERENCE_TYPE))
9099 			{
9100 			  decl_ref = decl;
9101 			  decl = TREE_OPERAND (decl, 0);
9102 			}
9103 		    }
9104 		}
9105 	      else if (TREE_CODE (decl) == COMPONENT_REF)
9106 		{
9107 		  while (TREE_CODE (decl) == COMPONENT_REF)
9108 		    decl = TREE_OPERAND (decl, 0);
9109 		  if (TREE_CODE (decl) == INDIRECT_REF
9110 		      && DECL_P (TREE_OPERAND (decl, 0))
9111 		      && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
9112 			  == REFERENCE_TYPE))
9113 		    decl = TREE_OPERAND (decl, 0);
9114 		}
9115 	      if (decl != orig_decl && DECL_P (decl) && indir_p)
9116 		{
9117 		  gomp_map_kind k
9118 		    = ((code == OACC_EXIT_DATA || code == OMP_TARGET_EXIT_DATA)
9119 		       ? GOMP_MAP_DETACH : GOMP_MAP_ATTACH);
9120 		  /* We have a dereference of a struct member.  Make this an
9121 		     attach/detach operation, and ensure the base pointer is
9122 		     mapped as a FIRSTPRIVATE_POINTER.  */
9123 		  OMP_CLAUSE_SET_MAP_KIND (c, k);
9124 		  flags = GOVD_MAP | GOVD_SEEN | GOVD_EXPLICIT;
9125 		  tree next_clause = OMP_CLAUSE_CHAIN (c);
9126 		  if (k == GOMP_MAP_ATTACH
9127 		      && code != OACC_ENTER_DATA
9128 		      && code != OMP_TARGET_ENTER_DATA
9129 		      && (!next_clause
9130 			   || (OMP_CLAUSE_CODE (next_clause) != OMP_CLAUSE_MAP)
9131 			   || (OMP_CLAUSE_MAP_KIND (next_clause)
9132 			       != GOMP_MAP_POINTER)
9133 			   || OMP_CLAUSE_DECL (next_clause) != decl)
9134 		      && (!struct_deref_set
9135 			  || !struct_deref_set->contains (decl)))
9136 		    {
9137 		      if (!struct_deref_set)
9138 			struct_deref_set = new hash_set<tree> ();
9139 		      /* As well as the attach, we also need a
9140 			 FIRSTPRIVATE_POINTER clause to properly map the
9141 			 pointer to the struct base.  */
9142 		      tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
9143 						  OMP_CLAUSE_MAP);
9144 		      OMP_CLAUSE_SET_MAP_KIND (c2, GOMP_MAP_ALLOC);
9145 		      OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (c2)
9146 			= 1;
9147 		      tree charptr_zero
9148 			= build_int_cst (build_pointer_type (char_type_node),
9149 					 0);
9150 		      OMP_CLAUSE_DECL (c2)
9151 			= build2 (MEM_REF, char_type_node,
9152 				  decl_ref ? decl_ref : decl, charptr_zero);
9153 		      OMP_CLAUSE_SIZE (c2) = size_zero_node;
9154 		      tree c3 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
9155 						  OMP_CLAUSE_MAP);
9156 		      OMP_CLAUSE_SET_MAP_KIND (c3,
9157 					       GOMP_MAP_FIRSTPRIVATE_POINTER);
9158 		      OMP_CLAUSE_DECL (c3) = decl;
9159 		      OMP_CLAUSE_SIZE (c3) = size_zero_node;
9160 		      tree mapgrp = *prev_list_p;
9161 		      *prev_list_p = c2;
9162 		      OMP_CLAUSE_CHAIN (c3) = mapgrp;
9163 		      OMP_CLAUSE_CHAIN (c2) = c3;
9164 
9165 		      struct_deref_set->add (decl);
9166 		    }
9167 		  goto do_add_decl;
9168 		}
9169 	      /* An "attach/detach" operation on an update directive should
9170 		 behave as a GOMP_MAP_ALWAYS_POINTER.  Beware that
9171 		 unlike attach or detach map kinds, GOMP_MAP_ALWAYS_POINTER
9172 		 depends on the previous mapping.  */
9173 	      if (code == OACC_UPDATE
9174 		  && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH)
9175 		OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_ALWAYS_POINTER);
9176 	      if (DECL_P (decl)
9177 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_TO_PSET
9178 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH
9179 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_DETACH
9180 		  && code != OACC_UPDATE
9181 		  && code != OMP_TARGET_UPDATE)
9182 		{
9183 		  if (error_operand_p (decl))
9184 		    {
9185 		      remove = true;
9186 		      break;
9187 		    }
9188 
9189 		  tree stype = TREE_TYPE (decl);
9190 		  if (TREE_CODE (stype) == REFERENCE_TYPE)
9191 		    stype = TREE_TYPE (stype);
9192 		  if (TYPE_SIZE_UNIT (stype) == NULL
9193 		      || TREE_CODE (TYPE_SIZE_UNIT (stype)) != INTEGER_CST)
9194 		    {
9195 		      error_at (OMP_CLAUSE_LOCATION (c),
9196 				"mapping field %qE of variable length "
9197 				"structure", OMP_CLAUSE_DECL (c));
9198 		      remove = true;
9199 		      break;
9200 		    }
9201 
9202 		  if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_POINTER
9203 		      || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH)
9204 		    {
9205 		      /* Error recovery.  */
9206 		      if (prev_list_p == NULL)
9207 			{
9208 			  remove = true;
9209 			  break;
9210 			}
9211 		      if (OMP_CLAUSE_CHAIN (*prev_list_p) != c)
9212 			{
9213 			  tree ch = OMP_CLAUSE_CHAIN (*prev_list_p);
9214 			  if (ch == NULL_TREE || OMP_CLAUSE_CHAIN (ch) != c)
9215 			    {
9216 			      remove = true;
9217 			      break;
9218 			    }
9219 			}
9220 		    }
9221 
9222 		  poly_offset_int offset1;
9223 		  poly_int64 bitpos1;
9224 		  tree base_ref;
9225 
9226 		  tree base
9227 		    = extract_base_bit_offset (OMP_CLAUSE_DECL (c), &base_ref,
9228 					       &bitpos1, &offset1);
9229 
9230 		  gcc_assert (base == decl);
9231 
9232 		  splay_tree_node n
9233 		    = splay_tree_lookup (ctx->variables, (splay_tree_key)decl);
9234 		  bool ptr = (OMP_CLAUSE_MAP_KIND (c)
9235 			      == GOMP_MAP_ALWAYS_POINTER);
9236 		  bool attach_detach = (OMP_CLAUSE_MAP_KIND (c)
9237 					== GOMP_MAP_ATTACH_DETACH);
9238 		  bool attach = OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH
9239 				|| OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_DETACH;
9240 		  bool has_attachments = false;
9241 		  /* For OpenACC, pointers in structs should trigger an
9242 		     attach action.  */
9243 		  if (attach_detach
9244 		      && ((region_type & (ORT_ACC | ORT_TARGET | ORT_TARGET_DATA))
9245 			  || code == OMP_TARGET_ENTER_DATA
9246 			  || code == OMP_TARGET_EXIT_DATA))
9247 
9248 		    {
9249 		      /* Turn a GOMP_MAP_ATTACH_DETACH clause into a
9250 			 GOMP_MAP_ATTACH or GOMP_MAP_DETACH clause after we
9251 			 have detected a case that needs a GOMP_MAP_STRUCT
9252 			 mapping added.  */
9253 		      gomp_map_kind k
9254 			= ((code == OACC_EXIT_DATA || code == OMP_TARGET_EXIT_DATA)
9255 			   ? GOMP_MAP_DETACH : GOMP_MAP_ATTACH);
9256 		      OMP_CLAUSE_SET_MAP_KIND (c, k);
9257 		      has_attachments = true;
9258 		    }
9259 		  if (n == NULL || (n->value & GOVD_MAP) == 0)
9260 		    {
9261 		      tree l = build_omp_clause (OMP_CLAUSE_LOCATION (c),
9262 						 OMP_CLAUSE_MAP);
9263 		      gomp_map_kind k = attach ? GOMP_MAP_FORCE_PRESENT
9264 					       : GOMP_MAP_STRUCT;
9265 
9266 		      OMP_CLAUSE_SET_MAP_KIND (l, k);
9267 		      if (base_ref)
9268 			OMP_CLAUSE_DECL (l) = unshare_expr (base_ref);
9269 		      else
9270 			OMP_CLAUSE_DECL (l) = decl;
9271 		      OMP_CLAUSE_SIZE (l)
9272 			= (!attach
9273 			   ? size_int (1)
9274 			   : DECL_P (OMP_CLAUSE_DECL (l))
9275 			   ? DECL_SIZE_UNIT (OMP_CLAUSE_DECL (l))
9276 			   : TYPE_SIZE_UNIT (TREE_TYPE (OMP_CLAUSE_DECL (l))));
9277 		      if (struct_map_to_clause == NULL)
9278 			struct_map_to_clause = new hash_map<tree, tree>;
9279 		      struct_map_to_clause->put (decl, l);
9280 		      if (ptr || attach_detach)
9281 			{
9282 			  insert_struct_comp_map (code, c, l, *prev_list_p,
9283 						  NULL);
9284 			  *prev_list_p = l;
9285 			  prev_list_p = NULL;
9286 			}
9287 		      else
9288 			{
9289 			  OMP_CLAUSE_CHAIN (l) = c;
9290 			  *list_p = l;
9291 			  list_p = &OMP_CLAUSE_CHAIN (l);
9292 			}
9293 		      if (base_ref && code == OMP_TARGET)
9294 			{
9295 			  tree c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
9296 						      OMP_CLAUSE_MAP);
9297 			  enum gomp_map_kind mkind
9298 			    = GOMP_MAP_FIRSTPRIVATE_REFERENCE;
9299 			  OMP_CLAUSE_SET_MAP_KIND (c2, mkind);
9300 			  OMP_CLAUSE_DECL (c2) = decl;
9301 			  OMP_CLAUSE_SIZE (c2) = size_zero_node;
9302 			  OMP_CLAUSE_CHAIN (c2) = OMP_CLAUSE_CHAIN (l);
9303 			  OMP_CLAUSE_CHAIN (l) = c2;
9304 			}
9305 		      flags = GOVD_MAP | GOVD_EXPLICIT;
9306 		      if (GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c))
9307 			  || ptr
9308 			  || attach_detach)
9309 			flags |= GOVD_SEEN;
9310 		      if (has_attachments)
9311 			flags |= GOVD_MAP_HAS_ATTACHMENTS;
9312 		      goto do_add_decl;
9313 		    }
9314 		  else if (struct_map_to_clause)
9315 		    {
9316 		      tree *osc = struct_map_to_clause->get (decl);
9317 		      tree *sc = NULL, *scp = NULL;
9318 		      if (GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c))
9319 			  || ptr
9320 			  || attach_detach)
9321 			n->value |= GOVD_SEEN;
9322 		      sc = &OMP_CLAUSE_CHAIN (*osc);
9323 		      if (*sc != c
9324 			  && (OMP_CLAUSE_MAP_KIND (*sc)
9325 			      == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
9326 			sc = &OMP_CLAUSE_CHAIN (*sc);
9327 		      /* Here "prev_list_p" is the end of the inserted
9328 			 alloc/release nodes after the struct node, OSC.  */
9329 		      for (; *sc != c; sc = &OMP_CLAUSE_CHAIN (*sc))
9330 			if ((ptr || attach_detach) && sc == prev_list_p)
9331 			  break;
9332 			else if (TREE_CODE (OMP_CLAUSE_DECL (*sc))
9333 				 != COMPONENT_REF
9334 				 && (TREE_CODE (OMP_CLAUSE_DECL (*sc))
9335 				     != INDIRECT_REF)
9336 				 && (TREE_CODE (OMP_CLAUSE_DECL (*sc))
9337 				     != ARRAY_REF))
9338 			  break;
9339 			else
9340 			  {
9341 			    tree sc_decl = OMP_CLAUSE_DECL (*sc);
9342 			    poly_offset_int offsetn;
9343 			    poly_int64 bitposn;
9344 			    tree base
9345 			      = extract_base_bit_offset (sc_decl, NULL,
9346 							 &bitposn, &offsetn);
9347 			    if (base != decl)
9348 			      break;
9349 			    if (scp)
9350 			      continue;
9351 			    if ((region_type & ORT_ACC) != 0)
9352 			      {
9353 				/* This duplicate checking code is currently only
9354 				   enabled for OpenACC.  */
9355 				tree d1 = OMP_CLAUSE_DECL (*sc);
9356 				tree d2 = OMP_CLAUSE_DECL (c);
9357 				while (TREE_CODE (d1) == ARRAY_REF)
9358 				  d1 = TREE_OPERAND (d1, 0);
9359 				while (TREE_CODE (d2) == ARRAY_REF)
9360 				  d2 = TREE_OPERAND (d2, 0);
9361 				if (TREE_CODE (d1) == INDIRECT_REF)
9362 				  d1 = TREE_OPERAND (d1, 0);
9363 				if (TREE_CODE (d2) == INDIRECT_REF)
9364 				  d2 = TREE_OPERAND (d2, 0);
9365 				while (TREE_CODE (d1) == COMPONENT_REF)
9366 				  if (TREE_CODE (d2) == COMPONENT_REF
9367 				      && TREE_OPERAND (d1, 1)
9368 				      == TREE_OPERAND (d2, 1))
9369 				    {
9370 				      d1 = TREE_OPERAND (d1, 0);
9371 				      d2 = TREE_OPERAND (d2, 0);
9372 				    }
9373 				  else
9374 				    break;
9375 				if (d1 == d2)
9376 				  {
9377 				    error_at (OMP_CLAUSE_LOCATION (c),
9378 					      "%qE appears more than once in map "
9379 					      "clauses", OMP_CLAUSE_DECL (c));
9380 				    remove = true;
9381 				    break;
9382 				  }
9383 			      }
9384 			    if (maybe_lt (offset1, offsetn)
9385 				|| (known_eq (offset1, offsetn)
9386 				    && maybe_lt (bitpos1, bitposn)))
9387 			      {
9388 				if (ptr || attach_detach)
9389 				  scp = sc;
9390 				else
9391 				  break;
9392 			      }
9393 			  }
9394 		      if (remove)
9395 			break;
9396 		      if (!attach)
9397 			OMP_CLAUSE_SIZE (*osc)
9398 			  = size_binop (PLUS_EXPR, OMP_CLAUSE_SIZE (*osc),
9399 					size_one_node);
9400 		      if (ptr || attach_detach)
9401 			{
9402 			  tree cl = insert_struct_comp_map (code, c, NULL,
9403 							    *prev_list_p, scp);
9404 			  if (sc == prev_list_p)
9405 			    {
9406 			      *sc = cl;
9407 			      prev_list_p = NULL;
9408 			    }
9409 			  else
9410 			    {
9411 			      *prev_list_p = OMP_CLAUSE_CHAIN (c);
9412 			      list_p = prev_list_p;
9413 			      prev_list_p = NULL;
9414 			      OMP_CLAUSE_CHAIN (c) = *sc;
9415 			      *sc = cl;
9416 			      continue;
9417 			    }
9418 			}
9419 		      else if (*sc != c)
9420 			{
9421 			  *list_p = OMP_CLAUSE_CHAIN (c);
9422 			  OMP_CLAUSE_CHAIN (c) = *sc;
9423 			  *sc = c;
9424 			  continue;
9425 			}
9426 		    }
9427 		}
9428 	      else if ((code == OACC_ENTER_DATA
9429 			|| code == OACC_EXIT_DATA
9430 			|| code == OACC_DATA
9431 			|| code == OACC_PARALLEL
9432 			|| code == OACC_KERNELS
9433 			|| code == OACC_SERIAL)
9434 		       && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH)
9435 		{
9436 		  gomp_map_kind k = (code == OACC_EXIT_DATA
9437 				     ? GOMP_MAP_DETACH : GOMP_MAP_ATTACH);
9438 		  OMP_CLAUSE_SET_MAP_KIND (c, k);
9439 		}
9440 
9441 	      if (gimplify_expr (pd, pre_p, NULL, is_gimple_lvalue, fb_lvalue)
9442 		  == GS_ERROR)
9443 		{
9444 		  remove = true;
9445 		  break;
9446 		}
9447 
9448 	      if (!remove
9449 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ALWAYS_POINTER
9450 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_ATTACH_DETACH
9451 		  && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_TO_PSET
9452 		  && OMP_CLAUSE_CHAIN (c)
9453 		  && OMP_CLAUSE_CODE (OMP_CLAUSE_CHAIN (c)) == OMP_CLAUSE_MAP
9454 		  && ((OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (c))
9455 		       == GOMP_MAP_ALWAYS_POINTER)
9456 		      || (OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (c))
9457 			  == GOMP_MAP_ATTACH_DETACH)
9458 		      || (OMP_CLAUSE_MAP_KIND (OMP_CLAUSE_CHAIN (c))
9459 			  == GOMP_MAP_TO_PSET)))
9460 		prev_list_p = list_p;
9461 
9462 	      break;
9463 	    }
9464 	  else
9465 	    {
9466 	      /* DECL_P (decl) == true  */
9467 	      tree *sc;
9468 	      if (struct_map_to_clause
9469 		  && (sc = struct_map_to_clause->get (decl)) != NULL
9470 		  && OMP_CLAUSE_MAP_KIND (*sc) == GOMP_MAP_STRUCT
9471 		  && decl == OMP_CLAUSE_DECL (*sc))
9472 		{
9473 		  /* We have found a map of the whole structure after a
9474 		     leading GOMP_MAP_STRUCT has been created, so refill the
9475 		     leading clause into a map of the whole structure
9476 		     variable, and remove the current one.
9477 		     TODO: we should be able to remove some maps of the
9478 		     following structure element maps if they are of
9479 		     compatible TO/FROM/ALLOC type.  */
9480 		  OMP_CLAUSE_SET_MAP_KIND (*sc, OMP_CLAUSE_MAP_KIND (c));
9481 		  OMP_CLAUSE_SIZE (*sc) = unshare_expr (OMP_CLAUSE_SIZE (c));
9482 		  remove = true;
9483 		  break;
9484 		}
9485 	    }
9486 	  flags = GOVD_MAP | GOVD_EXPLICIT;
9487 	  if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_TO
9488 	      || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_TOFROM)
9489 	    flags |= GOVD_MAP_ALWAYS_TO;
9490 
9491 	  if ((code == OMP_TARGET
9492 	       || code == OMP_TARGET_DATA
9493 	       || code == OMP_TARGET_ENTER_DATA
9494 	       || code == OMP_TARGET_EXIT_DATA)
9495 	      && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ATTACH_DETACH)
9496 	    {
9497 	      for (struct gimplify_omp_ctx *octx = outer_ctx; octx;
9498 		   octx = octx->outer_context)
9499 		{
9500 		  splay_tree_node n
9501 		    = splay_tree_lookup (octx->variables,
9502 					 (splay_tree_key) OMP_CLAUSE_DECL (c));
9503 		  /* If this is contained in an outer OpenMP region as a
9504 		     firstprivate value, remove the attach/detach.  */
9505 		  if (n && (n->value & GOVD_FIRSTPRIVATE))
9506 		    {
9507 		      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_FIRSTPRIVATE_POINTER);
9508 		      goto do_add;
9509 		    }
9510 		}
9511 
9512 	      enum gomp_map_kind map_kind = (code == OMP_TARGET_EXIT_DATA
9513 					     ? GOMP_MAP_DETACH
9514 					     : GOMP_MAP_ATTACH);
9515 	      OMP_CLAUSE_SET_MAP_KIND (c, map_kind);
9516 	    }
9517 
9518 	  goto do_add;
9519 
9520 	case OMP_CLAUSE_DEPEND:
9521 	  if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK)
9522 	    {
9523 	      tree deps = OMP_CLAUSE_DECL (c);
9524 	      while (deps && TREE_CODE (deps) == TREE_LIST)
9525 		{
9526 		  if (TREE_CODE (TREE_PURPOSE (deps)) == TRUNC_DIV_EXPR
9527 		      && DECL_P (TREE_OPERAND (TREE_PURPOSE (deps), 1)))
9528 		    gimplify_expr (&TREE_OPERAND (TREE_PURPOSE (deps), 1),
9529 				   pre_p, NULL, is_gimple_val, fb_rvalue);
9530 		  deps = TREE_CHAIN (deps);
9531 		}
9532 	      break;
9533 	    }
9534 	  else if (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE)
9535 	    break;
9536 	  if (handled_depend_iterators == -1)
9537 	    handled_depend_iterators = gimplify_omp_depend (list_p, pre_p);
9538 	  if (handled_depend_iterators)
9539 	    {
9540 	      if (handled_depend_iterators == 2)
9541 		remove = true;
9542 	      break;
9543 	    }
9544 	  if (TREE_CODE (OMP_CLAUSE_DECL (c)) == COMPOUND_EXPR)
9545 	    {
9546 	      gimplify_expr (&TREE_OPERAND (OMP_CLAUSE_DECL (c), 0), pre_p,
9547 			     NULL, is_gimple_val, fb_rvalue);
9548 	      OMP_CLAUSE_DECL (c) = TREE_OPERAND (OMP_CLAUSE_DECL (c), 1);
9549 	    }
9550 	  if (error_operand_p (OMP_CLAUSE_DECL (c)))
9551 	    {
9552 	      remove = true;
9553 	      break;
9554 	    }
9555 	  OMP_CLAUSE_DECL (c) = build_fold_addr_expr (OMP_CLAUSE_DECL (c));
9556 	  if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p, NULL,
9557 			     is_gimple_val, fb_rvalue) == GS_ERROR)
9558 	    {
9559 	      remove = true;
9560 	      break;
9561 	    }
9562 	  if (code == OMP_TASK)
9563 	    ctx->has_depend = true;
9564 	  break;
9565 
9566 	case OMP_CLAUSE_TO:
9567 	case OMP_CLAUSE_FROM:
9568 	case OMP_CLAUSE__CACHE_:
9569 	  decl = OMP_CLAUSE_DECL (c);
9570 	  if (error_operand_p (decl))
9571 	    {
9572 	      remove = true;
9573 	      break;
9574 	    }
9575 	  if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
9576 	    OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
9577 				  : TYPE_SIZE_UNIT (TREE_TYPE (decl));
9578 	  if (gimplify_expr (&OMP_CLAUSE_SIZE (c), pre_p,
9579 			     NULL, is_gimple_val, fb_rvalue) == GS_ERROR)
9580 	    {
9581 	      remove = true;
9582 	      break;
9583 	    }
9584 	  if (!DECL_P (decl))
9585 	    {
9586 	      if (gimplify_expr (&OMP_CLAUSE_DECL (c), pre_p,
9587 				 NULL, is_gimple_lvalue, fb_lvalue)
9588 		  == GS_ERROR)
9589 		{
9590 		  remove = true;
9591 		  break;
9592 		}
9593 	      break;
9594 	    }
9595 	  goto do_notice;
9596 
9597 	case OMP_CLAUSE_USE_DEVICE_PTR:
9598 	case OMP_CLAUSE_USE_DEVICE_ADDR:
9599 	  flags = GOVD_EXPLICIT;
9600 	  goto do_add;
9601 
9602 	case OMP_CLAUSE_IS_DEVICE_PTR:
9603 	  flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
9604 	  goto do_add;
9605 
9606 	do_add:
9607 	  decl = OMP_CLAUSE_DECL (c);
9608 	do_add_decl:
9609 	  if (error_operand_p (decl))
9610 	    {
9611 	      remove = true;
9612 	      break;
9613 	    }
9614 	  if (DECL_NAME (decl) == NULL_TREE && (flags & GOVD_SHARED) == 0)
9615 	    {
9616 	      tree t = omp_member_access_dummy_var (decl);
9617 	      if (t)
9618 		{
9619 		  tree v = DECL_VALUE_EXPR (decl);
9620 		  DECL_NAME (decl) = DECL_NAME (TREE_OPERAND (v, 1));
9621 		  if (outer_ctx)
9622 		    omp_notice_variable (outer_ctx, t, true);
9623 		}
9624 	    }
9625 	  if (code == OACC_DATA
9626 	      && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
9627 	      && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER)
9628 	    flags |= GOVD_MAP_0LEN_ARRAY;
9629 	  omp_add_variable (ctx, decl, flags);
9630 	  if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
9631 	       || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IN_REDUCTION
9632 	       || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_TASK_REDUCTION)
9633 	      && OMP_CLAUSE_REDUCTION_PLACEHOLDER (c))
9634 	    {
9635 	      omp_add_variable (ctx, OMP_CLAUSE_REDUCTION_PLACEHOLDER (c),
9636 				GOVD_LOCAL | GOVD_SEEN);
9637 	      if (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c)
9638 		  && walk_tree (&OMP_CLAUSE_REDUCTION_INIT (c),
9639 				find_decl_expr,
9640 				OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c),
9641 				NULL) == NULL_TREE)
9642 		omp_add_variable (ctx,
9643 				  OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c),
9644 				  GOVD_LOCAL | GOVD_SEEN);
9645 	      gimplify_omp_ctxp = ctx;
9646 	      push_gimplify_context ();
9647 
9648 	      OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c) = NULL;
9649 	      OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c) = NULL;
9650 
9651 	      gimplify_and_add (OMP_CLAUSE_REDUCTION_INIT (c),
9652 		  		&OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c));
9653 	      pop_gimplify_context
9654 		(gimple_seq_first_stmt (OMP_CLAUSE_REDUCTION_GIMPLE_INIT (c)));
9655 	      push_gimplify_context ();
9656 	      gimplify_and_add (OMP_CLAUSE_REDUCTION_MERGE (c),
9657 		  		&OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c));
9658 	      pop_gimplify_context
9659 		(gimple_seq_first_stmt (OMP_CLAUSE_REDUCTION_GIMPLE_MERGE (c)));
9660 	      OMP_CLAUSE_REDUCTION_INIT (c) = NULL_TREE;
9661 	      OMP_CLAUSE_REDUCTION_MERGE (c) = NULL_TREE;
9662 
9663 	      gimplify_omp_ctxp = outer_ctx;
9664 	    }
9665 	  else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
9666 		   && OMP_CLAUSE_LASTPRIVATE_STMT (c))
9667 	    {
9668 	      gimplify_omp_ctxp = ctx;
9669 	      push_gimplify_context ();
9670 	      if (TREE_CODE (OMP_CLAUSE_LASTPRIVATE_STMT (c)) != BIND_EXPR)
9671 		{
9672 		  tree bind = build3 (BIND_EXPR, void_type_node, NULL,
9673 				      NULL, NULL);
9674 		  TREE_SIDE_EFFECTS (bind) = 1;
9675 		  BIND_EXPR_BODY (bind) = OMP_CLAUSE_LASTPRIVATE_STMT (c);
9676 		  OMP_CLAUSE_LASTPRIVATE_STMT (c) = bind;
9677 		}
9678 	      gimplify_and_add (OMP_CLAUSE_LASTPRIVATE_STMT (c),
9679 				&OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c));
9680 	      pop_gimplify_context
9681 		(gimple_seq_first_stmt (OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c)));
9682 	      OMP_CLAUSE_LASTPRIVATE_STMT (c) = NULL_TREE;
9683 
9684 	      gimplify_omp_ctxp = outer_ctx;
9685 	    }
9686 	  else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
9687 		   && OMP_CLAUSE_LINEAR_STMT (c))
9688 	    {
9689 	      gimplify_omp_ctxp = ctx;
9690 	      push_gimplify_context ();
9691 	      if (TREE_CODE (OMP_CLAUSE_LINEAR_STMT (c)) != BIND_EXPR)
9692 		{
9693 		  tree bind = build3 (BIND_EXPR, void_type_node, NULL,
9694 				      NULL, NULL);
9695 		  TREE_SIDE_EFFECTS (bind) = 1;
9696 		  BIND_EXPR_BODY (bind) = OMP_CLAUSE_LINEAR_STMT (c);
9697 		  OMP_CLAUSE_LINEAR_STMT (c) = bind;
9698 		}
9699 	      gimplify_and_add (OMP_CLAUSE_LINEAR_STMT (c),
9700 				&OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c));
9701 	      pop_gimplify_context
9702 		(gimple_seq_first_stmt (OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c)));
9703 	      OMP_CLAUSE_LINEAR_STMT (c) = NULL_TREE;
9704 
9705 	      gimplify_omp_ctxp = outer_ctx;
9706 	    }
9707 	  if (notice_outer)
9708 	    goto do_notice;
9709 	  break;
9710 
9711 	case OMP_CLAUSE_COPYIN:
9712 	case OMP_CLAUSE_COPYPRIVATE:
9713 	  decl = OMP_CLAUSE_DECL (c);
9714 	  if (error_operand_p (decl))
9715 	    {
9716 	      remove = true;
9717 	      break;
9718 	    }
9719 	  if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_COPYPRIVATE
9720 	      && !remove
9721 	      && !omp_check_private (ctx, decl, true))
9722 	    {
9723 	      remove = true;
9724 	      if (is_global_var (decl))
9725 		{
9726 		  if (DECL_THREAD_LOCAL_P (decl))
9727 		    remove = false;
9728 		  else if (DECL_HAS_VALUE_EXPR_P (decl))
9729 		    {
9730 		      tree value = get_base_address (DECL_VALUE_EXPR (decl));
9731 
9732 		      if (value
9733 			  && DECL_P (value)
9734 			  && DECL_THREAD_LOCAL_P (value))
9735 			remove = false;
9736 		    }
9737 		}
9738 	      if (remove)
9739 		error_at (OMP_CLAUSE_LOCATION (c),
9740 			  "copyprivate variable %qE is not threadprivate"
9741 			  " or private in outer context", DECL_NAME (decl));
9742 	    }
9743 	do_notice:
9744 	  if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
9745 	       || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FIRSTPRIVATE
9746 	       || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE)
9747 	      && outer_ctx
9748 	      && ((region_type & ORT_TASKLOOP) == ORT_TASKLOOP
9749 		   || (region_type == ORT_WORKSHARE
9750 		       && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
9751 		       && (OMP_CLAUSE_REDUCTION_INSCAN (c)
9752 			   || code == OMP_LOOP)))
9753 	      && (outer_ctx->region_type == ORT_COMBINED_PARALLEL
9754 		  || (code == OMP_LOOP
9755 		      && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
9756 		      && ((outer_ctx->region_type & ORT_COMBINED_TEAMS)
9757 			  == ORT_COMBINED_TEAMS))))
9758 	    {
9759 	      splay_tree_node on
9760 		= splay_tree_lookup (outer_ctx->variables,
9761 				     (splay_tree_key)decl);
9762 	      if (on == NULL || (on->value & GOVD_DATA_SHARE_CLASS) == 0)
9763 		{
9764 		  if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION
9765 		      && TREE_CODE (OMP_CLAUSE_DECL (c)) == MEM_REF
9766 		      && (TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE
9767 			  || (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE
9768 			      && (TREE_CODE (TREE_TYPE (TREE_TYPE (decl)))
9769 				  == POINTER_TYPE))))
9770 		    omp_firstprivatize_variable (outer_ctx, decl);
9771 		  else
9772 		    {
9773 		      omp_add_variable (outer_ctx, decl,
9774 					GOVD_SEEN | GOVD_SHARED);
9775 		      if (outer_ctx->outer_context)
9776 			omp_notice_variable (outer_ctx->outer_context, decl,
9777 					     true);
9778 		    }
9779 		}
9780 	    }
9781 	  if (outer_ctx)
9782 	    omp_notice_variable (outer_ctx, decl, true);
9783 	  if (check_non_private
9784 	      && region_type == ORT_WORKSHARE
9785 	      && (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_REDUCTION
9786 		  || decl == OMP_CLAUSE_DECL (c)
9787 		  || (TREE_CODE (OMP_CLAUSE_DECL (c)) == MEM_REF
9788 		      && (TREE_CODE (TREE_OPERAND (OMP_CLAUSE_DECL (c), 0))
9789 			  == ADDR_EXPR
9790 			  || (TREE_CODE (TREE_OPERAND (OMP_CLAUSE_DECL (c), 0))
9791 			      == POINTER_PLUS_EXPR
9792 			      && (TREE_CODE (TREE_OPERAND (TREE_OPERAND
9793 						(OMP_CLAUSE_DECL (c), 0), 0))
9794 				  == ADDR_EXPR)))))
9795 	      && omp_check_private (ctx, decl, false))
9796 	    {
9797 	      error ("%s variable %qE is private in outer context",
9798 		     check_non_private, DECL_NAME (decl));
9799 	      remove = true;
9800 	    }
9801 	  break;
9802 
9803 	case OMP_CLAUSE_DETACH:
9804 	  flags = GOVD_FIRSTPRIVATE | GOVD_SEEN;
9805 	  goto do_add;
9806 
9807 	case OMP_CLAUSE_IF:
9808 	  if (OMP_CLAUSE_IF_MODIFIER (c) != ERROR_MARK
9809 	      && OMP_CLAUSE_IF_MODIFIER (c) != code)
9810 	    {
9811 	      const char *p[2];
9812 	      for (int i = 0; i < 2; i++)
9813 		switch (i ? OMP_CLAUSE_IF_MODIFIER (c) : code)
9814 		  {
9815 		  case VOID_CST: p[i] = "cancel"; break;
9816 		  case OMP_PARALLEL: p[i] = "parallel"; break;
9817 		  case OMP_SIMD: p[i] = "simd"; break;
9818 		  case OMP_TASK: p[i] = "task"; break;
9819 		  case OMP_TASKLOOP: p[i] = "taskloop"; break;
9820 		  case OMP_TARGET_DATA: p[i] = "target data"; break;
9821 		  case OMP_TARGET: p[i] = "target"; break;
9822 		  case OMP_TARGET_UPDATE: p[i] = "target update"; break;
9823 		  case OMP_TARGET_ENTER_DATA:
9824 		    p[i] = "target enter data"; break;
9825 		  case OMP_TARGET_EXIT_DATA: p[i] = "target exit data"; break;
9826 		  default: gcc_unreachable ();
9827 		  }
9828 	      error_at (OMP_CLAUSE_LOCATION (c),
9829 			"expected %qs %<if%> clause modifier rather than %qs",
9830 			p[0], p[1]);
9831 	      remove = true;
9832 	    }
9833 	  /* Fall through.  */
9834 
9835 	case OMP_CLAUSE_FINAL:
9836 	  OMP_CLAUSE_OPERAND (c, 0)
9837 	    = gimple_boolify (OMP_CLAUSE_OPERAND (c, 0));
9838 	  /* Fall through.  */
9839 
9840 	case OMP_CLAUSE_SCHEDULE:
9841 	case OMP_CLAUSE_NUM_THREADS:
9842 	case OMP_CLAUSE_NUM_TEAMS:
9843 	case OMP_CLAUSE_THREAD_LIMIT:
9844 	case OMP_CLAUSE_DIST_SCHEDULE:
9845 	case OMP_CLAUSE_DEVICE:
9846 	case OMP_CLAUSE_PRIORITY:
9847 	case OMP_CLAUSE_GRAINSIZE:
9848 	case OMP_CLAUSE_NUM_TASKS:
9849 	case OMP_CLAUSE_HINT:
9850 	case OMP_CLAUSE_ASYNC:
9851 	case OMP_CLAUSE_WAIT:
9852 	case OMP_CLAUSE_NUM_GANGS:
9853 	case OMP_CLAUSE_NUM_WORKERS:
9854 	case OMP_CLAUSE_VECTOR_LENGTH:
9855 	case OMP_CLAUSE_WORKER:
9856 	case OMP_CLAUSE_VECTOR:
9857 	  if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 0), pre_p, NULL,
9858 			     is_gimple_val, fb_rvalue) == GS_ERROR)
9859 	    remove = true;
9860 	  break;
9861 
9862 	case OMP_CLAUSE_GANG:
9863 	  if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 0), pre_p, NULL,
9864 			     is_gimple_val, fb_rvalue) == GS_ERROR)
9865 	    remove = true;
9866 	  if (gimplify_expr (&OMP_CLAUSE_OPERAND (c, 1), pre_p, NULL,
9867 			     is_gimple_val, fb_rvalue) == GS_ERROR)
9868 	    remove = true;
9869 	  break;
9870 
9871 	case OMP_CLAUSE_NOWAIT:
9872 	  nowait = 1;
9873 	  break;
9874 
9875 	case OMP_CLAUSE_ORDERED:
9876 	case OMP_CLAUSE_UNTIED:
9877 	case OMP_CLAUSE_COLLAPSE:
9878 	case OMP_CLAUSE_TILE:
9879 	case OMP_CLAUSE_AUTO:
9880 	case OMP_CLAUSE_SEQ:
9881 	case OMP_CLAUSE_INDEPENDENT:
9882 	case OMP_CLAUSE_MERGEABLE:
9883 	case OMP_CLAUSE_PROC_BIND:
9884 	case OMP_CLAUSE_SAFELEN:
9885 	case OMP_CLAUSE_SIMDLEN:
9886 	case OMP_CLAUSE_NOGROUP:
9887 	case OMP_CLAUSE_THREADS:
9888 	case OMP_CLAUSE_SIMD:
9889 	case OMP_CLAUSE_BIND:
9890 	case OMP_CLAUSE_IF_PRESENT:
9891 	case OMP_CLAUSE_FINALIZE:
9892 	  break;
9893 
9894 	case OMP_CLAUSE_ORDER:
9895 	  ctx->order_concurrent = true;
9896 	  break;
9897 
9898 	case OMP_CLAUSE_DEFAULTMAP:
9899 	  enum gimplify_defaultmap_kind gdmkmin, gdmkmax;
9900 	  switch (OMP_CLAUSE_DEFAULTMAP_CATEGORY (c))
9901 	    {
9902 	    case OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED:
9903 	      gdmkmin = GDMK_SCALAR;
9904 	      gdmkmax = GDMK_POINTER;
9905 	      break;
9906 	    case OMP_CLAUSE_DEFAULTMAP_CATEGORY_SCALAR:
9907 	      gdmkmin = gdmkmax = GDMK_SCALAR;
9908 	      break;
9909 	    case OMP_CLAUSE_DEFAULTMAP_CATEGORY_AGGREGATE:
9910 	      gdmkmin = gdmkmax = GDMK_AGGREGATE;
9911 	      break;
9912 	    case OMP_CLAUSE_DEFAULTMAP_CATEGORY_ALLOCATABLE:
9913 	      gdmkmin = gdmkmax = GDMK_ALLOCATABLE;
9914 	      break;
9915 	    case OMP_CLAUSE_DEFAULTMAP_CATEGORY_POINTER:
9916 	      gdmkmin = gdmkmax = GDMK_POINTER;
9917 	      break;
9918 	    default:
9919 	      gcc_unreachable ();
9920 	    }
9921 	  for (int gdmk = gdmkmin; gdmk <= gdmkmax; gdmk++)
9922 	    switch (OMP_CLAUSE_DEFAULTMAP_BEHAVIOR (c))
9923 	      {
9924 	      case OMP_CLAUSE_DEFAULTMAP_ALLOC:
9925 		ctx->defaultmap[gdmk] = GOVD_MAP | GOVD_MAP_ALLOC_ONLY;
9926 		break;
9927 	      case OMP_CLAUSE_DEFAULTMAP_TO:
9928 		ctx->defaultmap[gdmk] = GOVD_MAP | GOVD_MAP_TO_ONLY;
9929 		break;
9930 	      case OMP_CLAUSE_DEFAULTMAP_FROM:
9931 		ctx->defaultmap[gdmk] = GOVD_MAP | GOVD_MAP_FROM_ONLY;
9932 		break;
9933 	      case OMP_CLAUSE_DEFAULTMAP_TOFROM:
9934 		ctx->defaultmap[gdmk] = GOVD_MAP;
9935 		break;
9936 	      case OMP_CLAUSE_DEFAULTMAP_FIRSTPRIVATE:
9937 		ctx->defaultmap[gdmk] = GOVD_FIRSTPRIVATE;
9938 		break;
9939 	      case OMP_CLAUSE_DEFAULTMAP_NONE:
9940 		ctx->defaultmap[gdmk] = 0;
9941 		break;
9942 	      case OMP_CLAUSE_DEFAULTMAP_DEFAULT:
9943 		switch (gdmk)
9944 		  {
9945 		  case GDMK_SCALAR:
9946 		    ctx->defaultmap[gdmk] = GOVD_FIRSTPRIVATE;
9947 		    break;
9948 		  case GDMK_AGGREGATE:
9949 		  case GDMK_ALLOCATABLE:
9950 		    ctx->defaultmap[gdmk] = GOVD_MAP;
9951 		    break;
9952 		  case GDMK_POINTER:
9953 		    ctx->defaultmap[gdmk] = GOVD_MAP | GOVD_MAP_0LEN_ARRAY;
9954 		    break;
9955 		  default:
9956 		    gcc_unreachable ();
9957 		  }
9958 		break;
9959 	      default:
9960 		gcc_unreachable ();
9961 	      }
9962 	  break;
9963 
9964 	case OMP_CLAUSE_ALIGNED:
9965 	  decl = OMP_CLAUSE_DECL (c);
9966 	  if (error_operand_p (decl))
9967 	    {
9968 	      remove = true;
9969 	      break;
9970 	    }
9971 	  if (gimplify_expr (&OMP_CLAUSE_ALIGNED_ALIGNMENT (c), pre_p, NULL,
9972 			     is_gimple_val, fb_rvalue) == GS_ERROR)
9973 	    {
9974 	      remove = true;
9975 	      break;
9976 	    }
9977 	  if (!is_global_var (decl)
9978 	      && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
9979 	    omp_add_variable (ctx, decl, GOVD_ALIGNED);
9980 	  break;
9981 
9982 	case OMP_CLAUSE_NONTEMPORAL:
9983 	  decl = OMP_CLAUSE_DECL (c);
9984 	  if (error_operand_p (decl))
9985 	    {
9986 	      remove = true;
9987 	      break;
9988 	    }
9989 	  omp_add_variable (ctx, decl, GOVD_NONTEMPORAL);
9990 	  break;
9991 
9992 	case OMP_CLAUSE_ALLOCATE:
9993 	  decl = OMP_CLAUSE_DECL (c);
9994 	  if (error_operand_p (decl))
9995 	    {
9996 	      remove = true;
9997 	      break;
9998 	    }
9999 	  if (gimplify_expr (&OMP_CLAUSE_ALLOCATE_ALLOCATOR (c), pre_p, NULL,
10000 			     is_gimple_val, fb_rvalue) == GS_ERROR)
10001 	    {
10002 	      remove = true;
10003 	      break;
10004 	    }
10005 	  else if (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c) == NULL_TREE
10006 		   || (TREE_CODE (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c))
10007 		       == INTEGER_CST))
10008 	    ;
10009 	  else if (code == OMP_TASKLOOP
10010 		   || !DECL_P (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)))
10011 	    OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)
10012 	      = get_initialized_tmp_var (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c),
10013 					 pre_p, NULL, false);
10014 	  break;
10015 
10016 	case OMP_CLAUSE_DEFAULT:
10017 	  ctx->default_kind = OMP_CLAUSE_DEFAULT_KIND (c);
10018 	  break;
10019 
10020 	case OMP_CLAUSE_INCLUSIVE:
10021 	case OMP_CLAUSE_EXCLUSIVE:
10022 	  decl = OMP_CLAUSE_DECL (c);
10023 	  {
10024 	    splay_tree_node n = splay_tree_lookup (outer_ctx->variables,
10025 						   (splay_tree_key) decl);
10026 	    if (n == NULL || (n->value & GOVD_REDUCTION) == 0)
10027 	      {
10028 		error_at (OMP_CLAUSE_LOCATION (c),
10029 			  "%qD specified in %qs clause but not in %<inscan%> "
10030 			  "%<reduction%> clause on the containing construct",
10031 			  decl, omp_clause_code_name[OMP_CLAUSE_CODE (c)]);
10032 		remove = true;
10033 	      }
10034 	    else
10035 	      {
10036 		n->value |= GOVD_REDUCTION_INSCAN;
10037 		if (outer_ctx->region_type == ORT_SIMD
10038 		    && outer_ctx->outer_context
10039 		    && outer_ctx->outer_context->region_type == ORT_WORKSHARE)
10040 		  {
10041 		    n = splay_tree_lookup (outer_ctx->outer_context->variables,
10042 					   (splay_tree_key) decl);
10043 		    if (n && (n->value & GOVD_REDUCTION) != 0)
10044 		      n->value |= GOVD_REDUCTION_INSCAN;
10045 		  }
10046 	      }
10047 	  }
10048 	  break;
10049 
10050 	default:
10051 	  gcc_unreachable ();
10052 	}
10053 
10054       if (code == OACC_DATA
10055 	  && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP
10056 	  && (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
10057 	      || OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_REFERENCE))
10058 	remove = true;
10059       if (remove)
10060 	*list_p = OMP_CLAUSE_CHAIN (c);
10061       else
10062 	list_p = &OMP_CLAUSE_CHAIN (c);
10063     }
10064 
10065   ctx->clauses = *orig_list_p;
10066   gimplify_omp_ctxp = ctx;
10067   if (struct_map_to_clause)
10068     delete struct_map_to_clause;
10069   if (struct_deref_set)
10070     delete struct_deref_set;
10071 }
10072 
10073 /* Return true if DECL is a candidate for shared to firstprivate
10074    optimization.  We only consider non-addressable scalars, not
10075    too big, and not references.  */
10076 
10077 static bool
omp_shared_to_firstprivate_optimizable_decl_p(tree decl)10078 omp_shared_to_firstprivate_optimizable_decl_p (tree decl)
10079 {
10080   if (TREE_ADDRESSABLE (decl))
10081     return false;
10082   tree type = TREE_TYPE (decl);
10083   if (!is_gimple_reg_type (type)
10084       || TREE_CODE (type) == REFERENCE_TYPE
10085       || TREE_ADDRESSABLE (type))
10086     return false;
10087   /* Don't optimize too large decls, as each thread/task will have
10088      its own.  */
10089   HOST_WIDE_INT len = int_size_in_bytes (type);
10090   if (len == -1 || len > 4 * POINTER_SIZE / BITS_PER_UNIT)
10091     return false;
10092   if (lang_hooks.decls.omp_privatize_by_reference (decl))
10093     return false;
10094   return true;
10095 }
10096 
10097 /* Helper function of omp_find_stores_op and gimplify_adjust_omp_clauses*.
10098    For omp_shared_to_firstprivate_optimizable_decl_p decl mark it as
10099    GOVD_WRITTEN in outer contexts.  */
10100 
10101 static void
omp_mark_stores(struct gimplify_omp_ctx * ctx,tree decl)10102 omp_mark_stores (struct gimplify_omp_ctx *ctx, tree decl)
10103 {
10104   for (; ctx; ctx = ctx->outer_context)
10105     {
10106       splay_tree_node n = splay_tree_lookup (ctx->variables,
10107 					     (splay_tree_key) decl);
10108       if (n == NULL)
10109 	continue;
10110       else if (n->value & GOVD_SHARED)
10111 	{
10112 	  n->value |= GOVD_WRITTEN;
10113 	  return;
10114 	}
10115       else if (n->value & GOVD_DATA_SHARE_CLASS)
10116 	return;
10117     }
10118 }
10119 
10120 /* Helper callback for walk_gimple_seq to discover possible stores
10121    to omp_shared_to_firstprivate_optimizable_decl_p decls and set
10122    GOVD_WRITTEN if they are GOVD_SHARED in some outer context
10123    for those.  */
10124 
10125 static tree
omp_find_stores_op(tree * tp,int * walk_subtrees,void * data)10126 omp_find_stores_op (tree *tp, int *walk_subtrees, void *data)
10127 {
10128   struct walk_stmt_info *wi = (struct walk_stmt_info *) data;
10129 
10130   *walk_subtrees = 0;
10131   if (!wi->is_lhs)
10132     return NULL_TREE;
10133 
10134   tree op = *tp;
10135   do
10136     {
10137       if (handled_component_p (op))
10138 	op = TREE_OPERAND (op, 0);
10139       else if ((TREE_CODE (op) == MEM_REF || TREE_CODE (op) == TARGET_MEM_REF)
10140 	       && TREE_CODE (TREE_OPERAND (op, 0)) == ADDR_EXPR)
10141 	op = TREE_OPERAND (TREE_OPERAND (op, 0), 0);
10142       else
10143 	break;
10144     }
10145   while (1);
10146   if (!DECL_P (op) || !omp_shared_to_firstprivate_optimizable_decl_p (op))
10147     return NULL_TREE;
10148 
10149   omp_mark_stores (gimplify_omp_ctxp, op);
10150   return NULL_TREE;
10151 }
10152 
10153 /* Helper callback for walk_gimple_seq to discover possible stores
10154    to omp_shared_to_firstprivate_optimizable_decl_p decls and set
10155    GOVD_WRITTEN if they are GOVD_SHARED in some outer context
10156    for those.  */
10157 
10158 static tree
omp_find_stores_stmt(gimple_stmt_iterator * gsi_p,bool * handled_ops_p,struct walk_stmt_info * wi)10159 omp_find_stores_stmt (gimple_stmt_iterator *gsi_p,
10160 		      bool *handled_ops_p,
10161 		      struct walk_stmt_info *wi)
10162 {
10163   gimple *stmt = gsi_stmt (*gsi_p);
10164   switch (gimple_code (stmt))
10165     {
10166     /* Don't recurse on OpenMP constructs for which
10167        gimplify_adjust_omp_clauses already handled the bodies,
10168        except handle gimple_omp_for_pre_body.  */
10169     case GIMPLE_OMP_FOR:
10170       *handled_ops_p = true;
10171       if (gimple_omp_for_pre_body (stmt))
10172 	walk_gimple_seq (gimple_omp_for_pre_body (stmt),
10173 			 omp_find_stores_stmt, omp_find_stores_op, wi);
10174       break;
10175     case GIMPLE_OMP_PARALLEL:
10176     case GIMPLE_OMP_TASK:
10177     case GIMPLE_OMP_SECTIONS:
10178     case GIMPLE_OMP_SINGLE:
10179     case GIMPLE_OMP_TARGET:
10180     case GIMPLE_OMP_TEAMS:
10181     case GIMPLE_OMP_CRITICAL:
10182       *handled_ops_p = true;
10183       break;
10184     default:
10185       break;
10186     }
10187   return NULL_TREE;
10188 }
10189 
10190 struct gimplify_adjust_omp_clauses_data
10191 {
10192   tree *list_p;
10193   gimple_seq *pre_p;
10194 };
10195 
10196 /* For all variables that were not actually used within the context,
10197    remove PRIVATE, SHARED, and FIRSTPRIVATE clauses.  */
10198 
10199 static int
gimplify_adjust_omp_clauses_1(splay_tree_node n,void * data)10200 gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
10201 {
10202   tree *list_p = ((struct gimplify_adjust_omp_clauses_data *) data)->list_p;
10203   gimple_seq *pre_p
10204     = ((struct gimplify_adjust_omp_clauses_data *) data)->pre_p;
10205   tree decl = (tree) n->key;
10206   unsigned flags = n->value;
10207   enum omp_clause_code code;
10208   tree clause;
10209   bool private_debug;
10210 
10211   if (gimplify_omp_ctxp->region_type == ORT_COMBINED_PARALLEL
10212       && (flags & GOVD_LASTPRIVATE_CONDITIONAL) != 0)
10213     flags = GOVD_SHARED | GOVD_SEEN | GOVD_WRITTEN;
10214   if (flags & (GOVD_EXPLICIT | GOVD_LOCAL))
10215     return 0;
10216   if ((flags & GOVD_SEEN) == 0)
10217     return 0;
10218   if ((flags & GOVD_MAP_HAS_ATTACHMENTS) != 0)
10219     return 0;
10220   if (flags & GOVD_DEBUG_PRIVATE)
10221     {
10222       gcc_assert ((flags & GOVD_DATA_SHARE_CLASS) == GOVD_SHARED);
10223       private_debug = true;
10224     }
10225   else if (flags & GOVD_MAP)
10226     private_debug = false;
10227   else
10228     private_debug
10229       = lang_hooks.decls.omp_private_debug_clause (decl,
10230 						   !!(flags & GOVD_SHARED));
10231   if (private_debug)
10232     code = OMP_CLAUSE_PRIVATE;
10233   else if (flags & GOVD_MAP)
10234     {
10235       code = OMP_CLAUSE_MAP;
10236       if ((gimplify_omp_ctxp->region_type & ORT_ACC) == 0
10237 	  && TYPE_ATOMIC (strip_array_types (TREE_TYPE (decl))))
10238 	{
10239 	  error ("%<_Atomic%> %qD in implicit %<map%> clause", decl);
10240 	  return 0;
10241 	}
10242       if (VAR_P (decl)
10243 	  && DECL_IN_CONSTANT_POOL (decl)
10244           && !lookup_attribute ("omp declare target",
10245 				DECL_ATTRIBUTES (decl)))
10246 	{
10247 	  tree id = get_identifier ("omp declare target");
10248 	  DECL_ATTRIBUTES (decl)
10249 	    = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (decl));
10250 	  varpool_node *node = varpool_node::get (decl);
10251 	  if (node)
10252 	    {
10253 	      node->offloadable = 1;
10254 	      if (ENABLE_OFFLOADING)
10255 		g->have_offload = true;
10256 	    }
10257 	}
10258     }
10259   else if (flags & GOVD_SHARED)
10260     {
10261       if (is_global_var (decl))
10262 	{
10263 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp->outer_context;
10264 	  while (ctx != NULL)
10265 	    {
10266 	      splay_tree_node on
10267 		= splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10268 	      if (on && (on->value & (GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE
10269 				      | GOVD_PRIVATE | GOVD_REDUCTION
10270 				      | GOVD_LINEAR | GOVD_MAP)) != 0)
10271 		break;
10272 	      ctx = ctx->outer_context;
10273 	    }
10274 	  if (ctx == NULL)
10275 	    return 0;
10276 	}
10277       code = OMP_CLAUSE_SHARED;
10278       /* Don't optimize shared into firstprivate for read-only vars
10279 	 on tasks with depend clause, we shouldn't try to copy them
10280 	 until the dependencies are satisfied.  */
10281       if (gimplify_omp_ctxp->has_depend)
10282 	flags |= GOVD_WRITTEN;
10283     }
10284   else if (flags & GOVD_PRIVATE)
10285     code = OMP_CLAUSE_PRIVATE;
10286   else if (flags & GOVD_FIRSTPRIVATE)
10287     {
10288       code = OMP_CLAUSE_FIRSTPRIVATE;
10289       if ((gimplify_omp_ctxp->region_type & ORT_TARGET)
10290 	  && (gimplify_omp_ctxp->region_type & ORT_ACC) == 0
10291 	  && TYPE_ATOMIC (strip_array_types (TREE_TYPE (decl))))
10292 	{
10293 	  error ("%<_Atomic%> %qD in implicit %<firstprivate%> clause on "
10294 		 "%<target%> construct", decl);
10295 	  return 0;
10296 	}
10297     }
10298   else if (flags & GOVD_LASTPRIVATE)
10299     code = OMP_CLAUSE_LASTPRIVATE;
10300   else if (flags & (GOVD_ALIGNED | GOVD_NONTEMPORAL))
10301     return 0;
10302   else if (flags & GOVD_CONDTEMP)
10303     {
10304       code = OMP_CLAUSE__CONDTEMP_;
10305       gimple_add_tmp_var (decl);
10306     }
10307   else
10308     gcc_unreachable ();
10309 
10310   if (((flags & GOVD_LASTPRIVATE)
10311        || (code == OMP_CLAUSE_SHARED && (flags & GOVD_WRITTEN)))
10312       && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10313     omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
10314 
10315   tree chain = *list_p;
10316   clause = build_omp_clause (input_location, code);
10317   OMP_CLAUSE_DECL (clause) = decl;
10318   OMP_CLAUSE_CHAIN (clause) = chain;
10319   if (private_debug)
10320     OMP_CLAUSE_PRIVATE_DEBUG (clause) = 1;
10321   else if (code == OMP_CLAUSE_PRIVATE && (flags & GOVD_PRIVATE_OUTER_REF))
10322     OMP_CLAUSE_PRIVATE_OUTER_REF (clause) = 1;
10323   else if (code == OMP_CLAUSE_SHARED
10324 	   && (flags & GOVD_WRITTEN) == 0
10325 	   && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10326     OMP_CLAUSE_SHARED_READONLY (clause) = 1;
10327   else if (code == OMP_CLAUSE_FIRSTPRIVATE && (flags & GOVD_EXPLICIT) == 0)
10328     OMP_CLAUSE_FIRSTPRIVATE_IMPLICIT (clause) = 1;
10329   else if (code == OMP_CLAUSE_MAP && (flags & GOVD_MAP_0LEN_ARRAY) != 0)
10330     {
10331       tree nc = build_omp_clause (input_location, OMP_CLAUSE_MAP);
10332       OMP_CLAUSE_DECL (nc) = decl;
10333       if (TREE_CODE (TREE_TYPE (decl)) == REFERENCE_TYPE
10334 	  && TREE_CODE (TREE_TYPE (TREE_TYPE (decl))) == POINTER_TYPE)
10335 	OMP_CLAUSE_DECL (clause)
10336 	  = build_simple_mem_ref_loc (input_location, decl);
10337       OMP_CLAUSE_DECL (clause)
10338 	= build2 (MEM_REF, char_type_node, OMP_CLAUSE_DECL (clause),
10339 		  build_int_cst (build_pointer_type (char_type_node), 0));
10340       OMP_CLAUSE_SIZE (clause) = size_zero_node;
10341       OMP_CLAUSE_SIZE (nc) = size_zero_node;
10342       OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_ALLOC);
10343       OMP_CLAUSE_MAP_MAYBE_ZERO_LENGTH_ARRAY_SECTION (clause) = 1;
10344       OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_POINTER);
10345       OMP_CLAUSE_CHAIN (nc) = chain;
10346       OMP_CLAUSE_CHAIN (clause) = nc;
10347       struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
10348       gimplify_omp_ctxp = ctx->outer_context;
10349       gimplify_expr (&TREE_OPERAND (OMP_CLAUSE_DECL (clause), 0),
10350 		     pre_p, NULL, is_gimple_val, fb_rvalue);
10351       gimplify_omp_ctxp = ctx;
10352     }
10353   else if (code == OMP_CLAUSE_MAP)
10354     {
10355       int kind;
10356       /* Not all combinations of these GOVD_MAP flags are actually valid.  */
10357       switch (flags & (GOVD_MAP_TO_ONLY
10358 		       | GOVD_MAP_FORCE
10359 		       | GOVD_MAP_FORCE_PRESENT
10360 		       | GOVD_MAP_ALLOC_ONLY
10361 		       | GOVD_MAP_FROM_ONLY))
10362 	{
10363 	case 0:
10364 	  kind = GOMP_MAP_TOFROM;
10365 	  break;
10366 	case GOVD_MAP_FORCE:
10367 	  kind = GOMP_MAP_TOFROM | GOMP_MAP_FLAG_FORCE;
10368 	  break;
10369 	case GOVD_MAP_TO_ONLY:
10370 	  kind = GOMP_MAP_TO;
10371 	  break;
10372 	case GOVD_MAP_FROM_ONLY:
10373 	  kind = GOMP_MAP_FROM;
10374 	  break;
10375 	case GOVD_MAP_ALLOC_ONLY:
10376 	  kind = GOMP_MAP_ALLOC;
10377 	  break;
10378 	case GOVD_MAP_TO_ONLY | GOVD_MAP_FORCE:
10379 	  kind = GOMP_MAP_TO | GOMP_MAP_FLAG_FORCE;
10380 	  break;
10381 	case GOVD_MAP_FORCE_PRESENT:
10382 	  kind = GOMP_MAP_FORCE_PRESENT;
10383 	  break;
10384 	default:
10385 	  gcc_unreachable ();
10386 	}
10387       OMP_CLAUSE_SET_MAP_KIND (clause, kind);
10388       if (DECL_SIZE (decl)
10389 	  && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
10390 	{
10391 	  tree decl2 = DECL_VALUE_EXPR (decl);
10392 	  gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
10393 	  decl2 = TREE_OPERAND (decl2, 0);
10394 	  gcc_assert (DECL_P (decl2));
10395 	  tree mem = build_simple_mem_ref (decl2);
10396 	  OMP_CLAUSE_DECL (clause) = mem;
10397 	  OMP_CLAUSE_SIZE (clause) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
10398 	  if (gimplify_omp_ctxp->outer_context)
10399 	    {
10400 	      struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp->outer_context;
10401 	      omp_notice_variable (ctx, decl2, true);
10402 	      omp_notice_variable (ctx, OMP_CLAUSE_SIZE (clause), true);
10403 	    }
10404 	  tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (clause),
10405 				      OMP_CLAUSE_MAP);
10406 	  OMP_CLAUSE_DECL (nc) = decl;
10407 	  OMP_CLAUSE_SIZE (nc) = size_zero_node;
10408 	  if (gimplify_omp_ctxp->target_firstprivatize_array_bases)
10409 	    OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_POINTER);
10410 	  else
10411 	    OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_POINTER);
10412 	  OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (clause);
10413 	  OMP_CLAUSE_CHAIN (clause) = nc;
10414 	}
10415       else if (gimplify_omp_ctxp->target_firstprivatize_array_bases
10416 	       && lang_hooks.decls.omp_privatize_by_reference (decl))
10417 	{
10418 	  OMP_CLAUSE_DECL (clause) = build_simple_mem_ref (decl);
10419 	  OMP_CLAUSE_SIZE (clause)
10420 	    = unshare_expr (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (decl))));
10421 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
10422 	  gimplify_omp_ctxp = ctx->outer_context;
10423 	  gimplify_expr (&OMP_CLAUSE_SIZE (clause),
10424 			 pre_p, NULL, is_gimple_val, fb_rvalue);
10425 	  gimplify_omp_ctxp = ctx;
10426 	  tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (clause),
10427 				      OMP_CLAUSE_MAP);
10428 	  OMP_CLAUSE_DECL (nc) = decl;
10429 	  OMP_CLAUSE_SIZE (nc) = size_zero_node;
10430 	  OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_FIRSTPRIVATE_REFERENCE);
10431 	  OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (clause);
10432 	  OMP_CLAUSE_CHAIN (clause) = nc;
10433 	}
10434       else
10435 	OMP_CLAUSE_SIZE (clause) = DECL_SIZE_UNIT (decl);
10436     }
10437   if (code == OMP_CLAUSE_FIRSTPRIVATE && (flags & GOVD_LASTPRIVATE) != 0)
10438     {
10439       tree nc = build_omp_clause (input_location, OMP_CLAUSE_LASTPRIVATE);
10440       OMP_CLAUSE_DECL (nc) = decl;
10441       OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (nc) = 1;
10442       OMP_CLAUSE_CHAIN (nc) = chain;
10443       OMP_CLAUSE_CHAIN (clause) = nc;
10444       struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
10445       gimplify_omp_ctxp = ctx->outer_context;
10446       lang_hooks.decls.omp_finish_clause (nc, pre_p,
10447 					  (ctx->region_type & ORT_ACC) != 0);
10448       gimplify_omp_ctxp = ctx;
10449     }
10450   *list_p = clause;
10451   struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
10452   gimplify_omp_ctxp = ctx->outer_context;
10453   lang_hooks.decls.omp_finish_clause (clause, pre_p,
10454 				      (ctx->region_type & ORT_ACC) != 0);
10455   if (gimplify_omp_ctxp)
10456     for (; clause != chain; clause = OMP_CLAUSE_CHAIN (clause))
10457       if (OMP_CLAUSE_CODE (clause) == OMP_CLAUSE_MAP
10458 	  && DECL_P (OMP_CLAUSE_SIZE (clause)))
10459 	omp_notice_variable (gimplify_omp_ctxp, OMP_CLAUSE_SIZE (clause),
10460 			     true);
10461   gimplify_omp_ctxp = ctx;
10462   return 0;
10463 }
10464 
10465 static void
gimplify_adjust_omp_clauses(gimple_seq * pre_p,gimple_seq body,tree * list_p,enum tree_code code)10466 gimplify_adjust_omp_clauses (gimple_seq *pre_p, gimple_seq body, tree *list_p,
10467 			     enum tree_code code)
10468 {
10469   struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
10470   tree *orig_list_p = list_p;
10471   tree c, decl;
10472   bool has_inscan_reductions = false;
10473 
10474   if (body)
10475     {
10476       struct gimplify_omp_ctx *octx;
10477       for (octx = ctx; octx; octx = octx->outer_context)
10478 	if ((octx->region_type & (ORT_PARALLEL | ORT_TASK | ORT_TEAMS)) != 0)
10479 	  break;
10480       if (octx)
10481 	{
10482 	  struct walk_stmt_info wi;
10483 	  memset (&wi, 0, sizeof (wi));
10484 	  walk_gimple_seq (body, omp_find_stores_stmt,
10485 			   omp_find_stores_op, &wi);
10486 	}
10487     }
10488 
10489   if (ctx->add_safelen1)
10490     {
10491       /* If there are VLAs in the body of simd loop, prevent
10492 	 vectorization.  */
10493       gcc_assert (ctx->region_type == ORT_SIMD);
10494       c = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_SAFELEN);
10495       OMP_CLAUSE_SAFELEN_EXPR (c) = integer_one_node;
10496       OMP_CLAUSE_CHAIN (c) = *list_p;
10497       *list_p = c;
10498       list_p = &OMP_CLAUSE_CHAIN (c);
10499     }
10500 
10501   if (ctx->region_type == ORT_WORKSHARE
10502       && ctx->outer_context
10503       && ctx->outer_context->region_type == ORT_COMBINED_PARALLEL)
10504     {
10505       for (c = ctx->outer_context->clauses; c; c = OMP_CLAUSE_CHAIN (c))
10506 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
10507 	    && OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c))
10508 	  {
10509 	    decl = OMP_CLAUSE_DECL (c);
10510 	    splay_tree_node n
10511 	      = splay_tree_lookup (ctx->outer_context->variables,
10512 				   (splay_tree_key) decl);
10513 	    gcc_checking_assert (!splay_tree_lookup (ctx->variables,
10514 						     (splay_tree_key) decl));
10515 	    omp_add_variable (ctx, decl, n->value);
10516 	    tree c2 = copy_node (c);
10517 	    OMP_CLAUSE_CHAIN (c2) = *list_p;
10518 	    *list_p = c2;
10519 	    if ((n->value & GOVD_FIRSTPRIVATE) == 0)
10520 	      continue;
10521 	    c2 = build_omp_clause (OMP_CLAUSE_LOCATION (c),
10522 				   OMP_CLAUSE_FIRSTPRIVATE);
10523 	    OMP_CLAUSE_DECL (c2) = decl;
10524 	    OMP_CLAUSE_CHAIN (c2) = *list_p;
10525 	    *list_p = c2;
10526 	  }
10527     }
10528   while ((c = *list_p) != NULL)
10529     {
10530       splay_tree_node n;
10531       bool remove = false;
10532 
10533       switch (OMP_CLAUSE_CODE (c))
10534 	{
10535 	case OMP_CLAUSE_FIRSTPRIVATE:
10536 	  if ((ctx->region_type & ORT_TARGET)
10537 	      && (ctx->region_type & ORT_ACC) == 0
10538 	      && TYPE_ATOMIC (strip_array_types
10539 					(TREE_TYPE (OMP_CLAUSE_DECL (c)))))
10540 	    {
10541 	      error_at (OMP_CLAUSE_LOCATION (c),
10542 			"%<_Atomic%> %qD in %<firstprivate%> clause on "
10543 			"%<target%> construct", OMP_CLAUSE_DECL (c));
10544 	      remove = true;
10545 	      break;
10546 	    }
10547 	  /* FALLTHRU */
10548 	case OMP_CLAUSE_PRIVATE:
10549 	case OMP_CLAUSE_SHARED:
10550 	case OMP_CLAUSE_LINEAR:
10551 	  decl = OMP_CLAUSE_DECL (c);
10552 	  n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10553 	  remove = !(n->value & GOVD_SEEN);
10554 	  if ((n->value & GOVD_LASTPRIVATE_CONDITIONAL) != 0
10555 	      && code == OMP_PARALLEL
10556 	      && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_FIRSTPRIVATE)
10557 	    remove = true;
10558 	  if (! remove)
10559 	    {
10560 	      bool shared = OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED;
10561 	      if ((n->value & GOVD_DEBUG_PRIVATE)
10562 		  || lang_hooks.decls.omp_private_debug_clause (decl, shared))
10563 		{
10564 		  gcc_assert ((n->value & GOVD_DEBUG_PRIVATE) == 0
10565 			      || ((n->value & GOVD_DATA_SHARE_CLASS)
10566 				  == GOVD_SHARED));
10567 		  OMP_CLAUSE_SET_CODE (c, OMP_CLAUSE_PRIVATE);
10568 		  OMP_CLAUSE_PRIVATE_DEBUG (c) = 1;
10569 		}
10570               if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
10571 		  && ctx->has_depend
10572 		  && DECL_P (decl))
10573 		n->value |= GOVD_WRITTEN;
10574 	      if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
10575 		  && (n->value & GOVD_WRITTEN) == 0
10576 		  && DECL_P (decl)
10577 		  && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10578 		OMP_CLAUSE_SHARED_READONLY (c) = 1;
10579 	      else if (DECL_P (decl)
10580 		       && ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_SHARED
10581 			    && (n->value & GOVD_WRITTEN) != 0)
10582 			   || (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
10583 			       && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)))
10584 		       && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10585 		omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
10586 	    }
10587 	  else
10588 	    n->value &= ~GOVD_EXPLICIT;
10589 	  break;
10590 
10591 	case OMP_CLAUSE_LASTPRIVATE:
10592 	  /* Make sure OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE is set to
10593 	     accurately reflect the presence of a FIRSTPRIVATE clause.  */
10594 	  decl = OMP_CLAUSE_DECL (c);
10595 	  n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10596 	  OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c)
10597 	    = (n->value & GOVD_FIRSTPRIVATE) != 0;
10598 	  if (code == OMP_DISTRIBUTE
10599 	      && OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c))
10600 	    {
10601 	      remove = true;
10602 	      error_at (OMP_CLAUSE_LOCATION (c),
10603 			"same variable used in %<firstprivate%> and "
10604 			"%<lastprivate%> clauses on %<distribute%> "
10605 			"construct");
10606 	    }
10607 	  if (!remove
10608 	      && OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
10609 	      && DECL_P (decl)
10610 	      && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10611 	    omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
10612 	  if (OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) && code == OMP_PARALLEL)
10613 	    remove = true;
10614 	  break;
10615 
10616 	case OMP_CLAUSE_ALIGNED:
10617 	  decl = OMP_CLAUSE_DECL (c);
10618 	  if (!is_global_var (decl))
10619 	    {
10620 	      n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10621 	      remove = n == NULL || !(n->value & GOVD_SEEN);
10622 	      if (!remove && TREE_CODE (TREE_TYPE (decl)) == POINTER_TYPE)
10623 		{
10624 		  struct gimplify_omp_ctx *octx;
10625 		  if (n != NULL
10626 		      && (n->value & (GOVD_DATA_SHARE_CLASS
10627 				      & ~GOVD_FIRSTPRIVATE)))
10628 		    remove = true;
10629 		  else
10630 		    for (octx = ctx->outer_context; octx;
10631 			 octx = octx->outer_context)
10632 		      {
10633 			n = splay_tree_lookup (octx->variables,
10634 					       (splay_tree_key) decl);
10635 			if (n == NULL)
10636 			  continue;
10637 			if (n->value & GOVD_LOCAL)
10638 			  break;
10639 			/* We have to avoid assigning a shared variable
10640 			   to itself when trying to add
10641 			   __builtin_assume_aligned.  */
10642 			if (n->value & GOVD_SHARED)
10643 			  {
10644 			    remove = true;
10645 			    break;
10646 			  }
10647 		      }
10648 		}
10649 	    }
10650 	  else if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
10651 	    {
10652 	      n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10653 	      if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
10654 		remove = true;
10655 	    }
10656 	  break;
10657 
10658 	case OMP_CLAUSE_NONTEMPORAL:
10659 	  decl = OMP_CLAUSE_DECL (c);
10660 	  n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10661 	  remove = n == NULL || !(n->value & GOVD_SEEN);
10662 	  break;
10663 
10664 	case OMP_CLAUSE_MAP:
10665 	  if (code == OMP_TARGET_EXIT_DATA
10666 	      && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_ALWAYS_POINTER)
10667 	    {
10668 	      remove = true;
10669 	      break;
10670 	    }
10671 	  decl = OMP_CLAUSE_DECL (c);
10672 	  /* Data clauses associated with reductions must be
10673 	     compatible with present_or_copy.  Warn and adjust the clause
10674 	     if that is not the case.  */
10675 	  if (ctx->region_type == ORT_ACC_PARALLEL
10676 	      || ctx->region_type == ORT_ACC_SERIAL)
10677 	    {
10678 	      tree t = DECL_P (decl) ? decl : TREE_OPERAND (decl, 0);
10679 	      n = NULL;
10680 
10681 	      if (DECL_P (t))
10682 		n = splay_tree_lookup (ctx->variables, (splay_tree_key) t);
10683 
10684 	      if (n && (n->value & GOVD_REDUCTION))
10685 		{
10686 		  enum gomp_map_kind kind = OMP_CLAUSE_MAP_KIND (c);
10687 
10688 		  OMP_CLAUSE_MAP_IN_REDUCTION (c) = 1;
10689 		  if ((kind & GOMP_MAP_TOFROM) != GOMP_MAP_TOFROM
10690 		      && kind != GOMP_MAP_FORCE_PRESENT
10691 		      && kind != GOMP_MAP_POINTER)
10692 		    {
10693 		      warning_at (OMP_CLAUSE_LOCATION (c), 0,
10694 				  "incompatible data clause with reduction "
10695 				  "on %qE; promoting to %<present_or_copy%>",
10696 				  DECL_NAME (t));
10697 		      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_TOFROM);
10698 		    }
10699 		}
10700 	    }
10701 	  if (!DECL_P (decl))
10702 	    {
10703 	      if ((ctx->region_type & ORT_TARGET) != 0
10704 		  && OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER)
10705 		{
10706 		  if (TREE_CODE (decl) == INDIRECT_REF
10707 		      && TREE_CODE (TREE_OPERAND (decl, 0)) == COMPONENT_REF
10708 		      && (TREE_CODE (TREE_TYPE (TREE_OPERAND (decl, 0)))
10709 			  == REFERENCE_TYPE))
10710 		    decl = TREE_OPERAND (decl, 0);
10711 		  if (TREE_CODE (decl) == COMPONENT_REF)
10712 		    {
10713 		      while (TREE_CODE (decl) == COMPONENT_REF)
10714 			decl = TREE_OPERAND (decl, 0);
10715 		      if (DECL_P (decl))
10716 			{
10717 			  n = splay_tree_lookup (ctx->variables,
10718 						 (splay_tree_key) decl);
10719 			  if (!(n->value & GOVD_SEEN))
10720 			    remove = true;
10721 			}
10722 		    }
10723 		}
10724 	      break;
10725 	    }
10726 	  n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10727 	  if ((ctx->region_type & ORT_TARGET) != 0
10728 	      && !(n->value & GOVD_SEEN)
10729 	      && GOMP_MAP_ALWAYS_P (OMP_CLAUSE_MAP_KIND (c)) == 0
10730 	      && (!is_global_var (decl)
10731 		  || !lookup_attribute ("omp declare target link",
10732 					DECL_ATTRIBUTES (decl))))
10733 	    {
10734 	      remove = true;
10735 	      /* For struct element mapping, if struct is never referenced
10736 		 in target block and none of the mapping has always modifier,
10737 		 remove all the struct element mappings, which immediately
10738 		 follow the GOMP_MAP_STRUCT map clause.  */
10739 	      if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_STRUCT)
10740 		{
10741 		  HOST_WIDE_INT cnt = tree_to_shwi (OMP_CLAUSE_SIZE (c));
10742 		  while (cnt--)
10743 		    OMP_CLAUSE_CHAIN (c)
10744 		      = OMP_CLAUSE_CHAIN (OMP_CLAUSE_CHAIN (c));
10745 		}
10746 	    }
10747 	  else if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_STRUCT
10748 		   && (code == OMP_TARGET_EXIT_DATA
10749 		       || code == OACC_EXIT_DATA))
10750 	    remove = true;
10751 	  else if (DECL_SIZE (decl)
10752 		   && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST
10753 		   && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_POINTER
10754 		   && OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FIRSTPRIVATE_POINTER
10755 		   && (OMP_CLAUSE_MAP_KIND (c)
10756 		       != GOMP_MAP_FIRSTPRIVATE_REFERENCE))
10757 	    {
10758 	      /* For GOMP_MAP_FORCE_DEVICEPTR, we'll never enter here, because
10759 		 for these, TREE_CODE (DECL_SIZE (decl)) will always be
10760 		 INTEGER_CST.  */
10761 	      gcc_assert (OMP_CLAUSE_MAP_KIND (c) != GOMP_MAP_FORCE_DEVICEPTR);
10762 
10763 	      tree decl2 = DECL_VALUE_EXPR (decl);
10764 	      gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
10765 	      decl2 = TREE_OPERAND (decl2, 0);
10766 	      gcc_assert (DECL_P (decl2));
10767 	      tree mem = build_simple_mem_ref (decl2);
10768 	      OMP_CLAUSE_DECL (c) = mem;
10769 	      OMP_CLAUSE_SIZE (c) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
10770 	      if (ctx->outer_context)
10771 		{
10772 		  omp_notice_variable (ctx->outer_context, decl2, true);
10773 		  omp_notice_variable (ctx->outer_context,
10774 				       OMP_CLAUSE_SIZE (c), true);
10775 		}
10776 	      if (((ctx->region_type & ORT_TARGET) != 0
10777 		   || !ctx->target_firstprivatize_array_bases)
10778 		  && ((n->value & GOVD_SEEN) == 0
10779 		      || (n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE)) == 0))
10780 		{
10781 		  tree nc = build_omp_clause (OMP_CLAUSE_LOCATION (c),
10782 					      OMP_CLAUSE_MAP);
10783 		  OMP_CLAUSE_DECL (nc) = decl;
10784 		  OMP_CLAUSE_SIZE (nc) = size_zero_node;
10785 		  if (ctx->target_firstprivatize_array_bases)
10786 		    OMP_CLAUSE_SET_MAP_KIND (nc,
10787 					     GOMP_MAP_FIRSTPRIVATE_POINTER);
10788 		  else
10789 		    OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_POINTER);
10790 		  OMP_CLAUSE_CHAIN (nc) = OMP_CLAUSE_CHAIN (c);
10791 		  OMP_CLAUSE_CHAIN (c) = nc;
10792 		  c = nc;
10793 		}
10794 	    }
10795 	  else
10796 	    {
10797 	      if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
10798 		OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
10799 	      gcc_assert ((n->value & GOVD_SEEN) == 0
10800 			  || ((n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE))
10801 			      == 0));
10802 	    }
10803 	  break;
10804 
10805 	case OMP_CLAUSE_TO:
10806 	case OMP_CLAUSE_FROM:
10807 	case OMP_CLAUSE__CACHE_:
10808 	  decl = OMP_CLAUSE_DECL (c);
10809 	  if (!DECL_P (decl))
10810 	    break;
10811 	  if (DECL_SIZE (decl)
10812 	      && TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
10813 	    {
10814 	      tree decl2 = DECL_VALUE_EXPR (decl);
10815 	      gcc_assert (TREE_CODE (decl2) == INDIRECT_REF);
10816 	      decl2 = TREE_OPERAND (decl2, 0);
10817 	      gcc_assert (DECL_P (decl2));
10818 	      tree mem = build_simple_mem_ref (decl2);
10819 	      OMP_CLAUSE_DECL (c) = mem;
10820 	      OMP_CLAUSE_SIZE (c) = TYPE_SIZE_UNIT (TREE_TYPE (decl));
10821 	      if (ctx->outer_context)
10822 		{
10823 		  omp_notice_variable (ctx->outer_context, decl2, true);
10824 		  omp_notice_variable (ctx->outer_context,
10825 				       OMP_CLAUSE_SIZE (c), true);
10826 		}
10827 	    }
10828 	  else if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
10829 	    OMP_CLAUSE_SIZE (c) = DECL_SIZE_UNIT (decl);
10830 	  break;
10831 
10832 	case OMP_CLAUSE_REDUCTION:
10833 	  if (OMP_CLAUSE_REDUCTION_INSCAN (c))
10834 	    {
10835 	      decl = OMP_CLAUSE_DECL (c);
10836 	      n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10837 	      if ((n->value & GOVD_REDUCTION_INSCAN) == 0)
10838 		{
10839 		  remove = true;
10840 		  error_at (OMP_CLAUSE_LOCATION (c),
10841 			    "%qD specified in %<inscan%> %<reduction%> clause "
10842 			    "but not in %<scan%> directive clause", decl);
10843 		  break;
10844 		}
10845 	      has_inscan_reductions = true;
10846 	    }
10847 	  /* FALLTHRU */
10848 	case OMP_CLAUSE_IN_REDUCTION:
10849 	case OMP_CLAUSE_TASK_REDUCTION:
10850 	  decl = OMP_CLAUSE_DECL (c);
10851 	  /* OpenACC reductions need a present_or_copy data clause.
10852 	     Add one if necessary.  Emit error when the reduction is private.  */
10853 	  if (ctx->region_type == ORT_ACC_PARALLEL
10854 	      || ctx->region_type == ORT_ACC_SERIAL)
10855 	    {
10856 	      n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10857 	      if (n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE))
10858 		{
10859 		  remove = true;
10860 		  error_at (OMP_CLAUSE_LOCATION (c), "invalid private "
10861 			    "reduction on %qE", DECL_NAME (decl));
10862 		}
10863 	      else if ((n->value & GOVD_MAP) == 0)
10864 		{
10865 		  tree next = OMP_CLAUSE_CHAIN (c);
10866 		  tree nc = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_MAP);
10867 		  OMP_CLAUSE_SET_MAP_KIND (nc, GOMP_MAP_TOFROM);
10868 		  OMP_CLAUSE_DECL (nc) = decl;
10869 		  OMP_CLAUSE_CHAIN (c) = nc;
10870 		  lang_hooks.decls.omp_finish_clause (nc, pre_p,
10871 						      (ctx->region_type
10872 						       & ORT_ACC) != 0);
10873 		  while (1)
10874 		    {
10875 		      OMP_CLAUSE_MAP_IN_REDUCTION (nc) = 1;
10876 		      if (OMP_CLAUSE_CHAIN (nc) == NULL)
10877 			break;
10878 		      nc = OMP_CLAUSE_CHAIN (nc);
10879 		    }
10880 		  OMP_CLAUSE_CHAIN (nc) = next;
10881 		  n->value |= GOVD_MAP;
10882 		}
10883 	    }
10884 	  if (DECL_P (decl)
10885 	      && omp_shared_to_firstprivate_optimizable_decl_p (decl))
10886 	    omp_mark_stores (gimplify_omp_ctxp->outer_context, decl);
10887 	  break;
10888 
10889 	case OMP_CLAUSE_ALLOCATE:
10890 	  decl = OMP_CLAUSE_DECL (c);
10891 	  n = splay_tree_lookup (ctx->variables, (splay_tree_key) decl);
10892 	  if (n != NULL && !(n->value & GOVD_SEEN))
10893 	    {
10894 	      if ((n->value & (GOVD_PRIVATE | GOVD_FIRSTPRIVATE | GOVD_LINEAR))
10895 		  != 0
10896 		  && (n->value & (GOVD_REDUCTION | GOVD_LASTPRIVATE)) == 0)
10897 		remove = true;
10898 	    }
10899 	  if (!remove
10900 	      && OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)
10901 	      && TREE_CODE (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)) != INTEGER_CST
10902 	      && ((ctx->region_type & (ORT_PARALLEL | ORT_TARGET)) != 0
10903 		  || (ctx->region_type & ORT_TASKLOOP) == ORT_TASK
10904 		  || (ctx->region_type & ORT_HOST_TEAMS) == ORT_HOST_TEAMS))
10905 	    {
10906 	      tree allocator = OMP_CLAUSE_ALLOCATE_ALLOCATOR (c);
10907 	      n = splay_tree_lookup (ctx->variables, (splay_tree_key) allocator);
10908 	      if (n == NULL)
10909 		{
10910 		  enum omp_clause_default_kind default_kind
10911 		    = ctx->default_kind;
10912 		  ctx->default_kind = OMP_CLAUSE_DEFAULT_FIRSTPRIVATE;
10913 		  omp_notice_variable (ctx, OMP_CLAUSE_ALLOCATE_ALLOCATOR (c),
10914 				       true);
10915 		  ctx->default_kind = default_kind;
10916 		}
10917 	      else
10918 		omp_notice_variable (ctx, OMP_CLAUSE_ALLOCATE_ALLOCATOR (c),
10919 				     true);
10920 	    }
10921 	  break;
10922 
10923 	case OMP_CLAUSE_COPYIN:
10924 	case OMP_CLAUSE_COPYPRIVATE:
10925 	case OMP_CLAUSE_IF:
10926 	case OMP_CLAUSE_NUM_THREADS:
10927 	case OMP_CLAUSE_NUM_TEAMS:
10928 	case OMP_CLAUSE_THREAD_LIMIT:
10929 	case OMP_CLAUSE_DIST_SCHEDULE:
10930 	case OMP_CLAUSE_DEVICE:
10931 	case OMP_CLAUSE_SCHEDULE:
10932 	case OMP_CLAUSE_NOWAIT:
10933 	case OMP_CLAUSE_ORDERED:
10934 	case OMP_CLAUSE_DEFAULT:
10935 	case OMP_CLAUSE_UNTIED:
10936 	case OMP_CLAUSE_COLLAPSE:
10937 	case OMP_CLAUSE_FINAL:
10938 	case OMP_CLAUSE_MERGEABLE:
10939 	case OMP_CLAUSE_PROC_BIND:
10940 	case OMP_CLAUSE_SAFELEN:
10941 	case OMP_CLAUSE_SIMDLEN:
10942 	case OMP_CLAUSE_DEPEND:
10943 	case OMP_CLAUSE_PRIORITY:
10944 	case OMP_CLAUSE_GRAINSIZE:
10945 	case OMP_CLAUSE_NUM_TASKS:
10946 	case OMP_CLAUSE_NOGROUP:
10947 	case OMP_CLAUSE_THREADS:
10948 	case OMP_CLAUSE_SIMD:
10949 	case OMP_CLAUSE_HINT:
10950 	case OMP_CLAUSE_DEFAULTMAP:
10951 	case OMP_CLAUSE_ORDER:
10952 	case OMP_CLAUSE_BIND:
10953 	case OMP_CLAUSE_DETACH:
10954 	case OMP_CLAUSE_USE_DEVICE_PTR:
10955 	case OMP_CLAUSE_USE_DEVICE_ADDR:
10956 	case OMP_CLAUSE_IS_DEVICE_PTR:
10957 	case OMP_CLAUSE_ASYNC:
10958 	case OMP_CLAUSE_WAIT:
10959 	case OMP_CLAUSE_INDEPENDENT:
10960 	case OMP_CLAUSE_NUM_GANGS:
10961 	case OMP_CLAUSE_NUM_WORKERS:
10962 	case OMP_CLAUSE_VECTOR_LENGTH:
10963 	case OMP_CLAUSE_GANG:
10964 	case OMP_CLAUSE_WORKER:
10965 	case OMP_CLAUSE_VECTOR:
10966 	case OMP_CLAUSE_AUTO:
10967 	case OMP_CLAUSE_SEQ:
10968 	case OMP_CLAUSE_TILE:
10969 	case OMP_CLAUSE_IF_PRESENT:
10970 	case OMP_CLAUSE_FINALIZE:
10971 	case OMP_CLAUSE_INCLUSIVE:
10972 	case OMP_CLAUSE_EXCLUSIVE:
10973 	  break;
10974 
10975 	default:
10976 	  gcc_unreachable ();
10977 	}
10978 
10979       if (remove)
10980 	*list_p = OMP_CLAUSE_CHAIN (c);
10981       else
10982 	list_p = &OMP_CLAUSE_CHAIN (c);
10983     }
10984 
10985   /* Add in any implicit data sharing.  */
10986   struct gimplify_adjust_omp_clauses_data data;
10987   data.list_p = list_p;
10988   data.pre_p = pre_p;
10989   splay_tree_foreach (ctx->variables, gimplify_adjust_omp_clauses_1, &data);
10990 
10991   if (has_inscan_reductions)
10992     for (c = *orig_list_p; c; c = OMP_CLAUSE_CHAIN (c))
10993       if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
10994 	  && !OMP_CLAUSE_LINEAR_NO_COPYIN (c))
10995 	{
10996 	  error_at (OMP_CLAUSE_LOCATION (c),
10997 		    "%<inscan%> %<reduction%> clause used together with "
10998 		    "%<linear%> clause for a variable other than loop "
10999 		    "iterator");
11000 	  break;
11001 	}
11002 
11003   gimplify_omp_ctxp = ctx->outer_context;
11004   delete_omp_context (ctx);
11005 }
11006 
11007 /* Return 0 if CONSTRUCTS selectors don't match the OpenMP context,
11008    -1 if unknown yet (simd is involved, won't be known until vectorization)
11009    and 1 if they do.  If SCORES is non-NULL, it should point to an array
11010    of at least 2*NCONSTRUCTS+2 ints, and will be filled with the positions
11011    of the CONSTRUCTS (position -1 if it will never match) followed by
11012    number of constructs in the OpenMP context construct trait.  If the
11013    score depends on whether it will be in a declare simd clone or not,
11014    the function returns 2 and there will be two sets of the scores, the first
11015    one for the case that it is not in a declare simd clone, the other
11016    that it is in a declare simd clone.  */
11017 
11018 int
omp_construct_selector_matches(enum tree_code * constructs,int nconstructs,int * scores)11019 omp_construct_selector_matches (enum tree_code *constructs, int nconstructs,
11020 				int *scores)
11021 {
11022   int matched = 0, cnt = 0;
11023   bool simd_seen = false;
11024   bool target_seen = false;
11025   int declare_simd_cnt = -1;
11026   auto_vec<enum tree_code, 16> codes;
11027   for (struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp; ctx;)
11028     {
11029       if (((ctx->region_type & ORT_PARALLEL) && ctx->code == OMP_PARALLEL)
11030 	  || ((ctx->region_type & (ORT_TARGET | ORT_IMPLICIT_TARGET | ORT_ACC))
11031 	      == ORT_TARGET && ctx->code == OMP_TARGET)
11032 	  || ((ctx->region_type & ORT_TEAMS) && ctx->code == OMP_TEAMS)
11033 	  || (ctx->region_type == ORT_WORKSHARE && ctx->code == OMP_FOR)
11034 	  || (ctx->region_type == ORT_SIMD
11035 	      && ctx->code == OMP_SIMD
11036 	      && !omp_find_clause (ctx->clauses, OMP_CLAUSE_BIND)))
11037 	{
11038 	  ++cnt;
11039 	  if (scores)
11040 	    codes.safe_push (ctx->code);
11041 	  else if (matched < nconstructs && ctx->code == constructs[matched])
11042 	    {
11043 	      if (ctx->code == OMP_SIMD)
11044 		{
11045 		  if (matched)
11046 		    return 0;
11047 		  simd_seen = true;
11048 		}
11049 	      ++matched;
11050 	    }
11051 	  if (ctx->code == OMP_TARGET)
11052 	    {
11053 	      if (scores == NULL)
11054 		return matched < nconstructs ? 0 : simd_seen ? -1 : 1;
11055 	      target_seen = true;
11056 	      break;
11057 	    }
11058 	}
11059       else if (ctx->region_type == ORT_WORKSHARE
11060 	       && ctx->code == OMP_LOOP
11061 	       && ctx->outer_context
11062 	       && ctx->outer_context->region_type == ORT_COMBINED_PARALLEL
11063 	       && ctx->outer_context->outer_context
11064 	       && ctx->outer_context->outer_context->code == OMP_LOOP
11065 	       && ctx->outer_context->outer_context->distribute)
11066 	ctx = ctx->outer_context->outer_context;
11067       ctx = ctx->outer_context;
11068     }
11069   if (!target_seen
11070       && lookup_attribute ("omp declare simd",
11071 			   DECL_ATTRIBUTES (current_function_decl)))
11072     {
11073       /* Declare simd is a maybe case, it is supposed to be added only to the
11074 	 omp-simd-clone.c added clones and not to the base function.  */
11075       declare_simd_cnt = cnt++;
11076       if (scores)
11077 	codes.safe_push (OMP_SIMD);
11078       else if (cnt == 0
11079 	       && constructs[0] == OMP_SIMD)
11080 	{
11081 	  gcc_assert (matched == 0);
11082 	  simd_seen = true;
11083 	  if (++matched == nconstructs)
11084 	    return -1;
11085 	}
11086     }
11087   if (tree attr = lookup_attribute ("omp declare variant variant",
11088 				    DECL_ATTRIBUTES (current_function_decl)))
11089     {
11090       enum tree_code variant_constructs[5];
11091       int variant_nconstructs = 0;
11092       if (!target_seen)
11093 	variant_nconstructs
11094 	  = omp_constructor_traits_to_codes (TREE_VALUE (attr),
11095 					     variant_constructs);
11096       for (int i = 0; i < variant_nconstructs; i++)
11097 	{
11098 	  ++cnt;
11099 	  if (scores)
11100 	    codes.safe_push (variant_constructs[i]);
11101 	  else if (matched < nconstructs
11102 		   && variant_constructs[i] == constructs[matched])
11103 	    {
11104 	      if (variant_constructs[i] == OMP_SIMD)
11105 		{
11106 		  if (matched)
11107 		    return 0;
11108 		  simd_seen = true;
11109 		}
11110 	      ++matched;
11111 	    }
11112 	}
11113     }
11114   if (!target_seen
11115       && lookup_attribute ("omp declare target block",
11116 			   DECL_ATTRIBUTES (current_function_decl)))
11117     {
11118       if (scores)
11119 	codes.safe_push (OMP_TARGET);
11120       else if (matched < nconstructs && constructs[matched] == OMP_TARGET)
11121 	++matched;
11122     }
11123   if (scores)
11124     {
11125       for (int pass = 0; pass < (declare_simd_cnt == -1 ? 1 : 2); pass++)
11126 	{
11127 	  int j = codes.length () - 1;
11128 	  for (int i = nconstructs - 1; i >= 0; i--)
11129 	    {
11130 	      while (j >= 0
11131 		     && (pass != 0 || declare_simd_cnt != j)
11132 		     && constructs[i] != codes[j])
11133 		--j;
11134 	      if (pass == 0 && declare_simd_cnt != -1 && j > declare_simd_cnt)
11135 		*scores++ = j - 1;
11136 	      else
11137 		*scores++ = j;
11138 	    }
11139 	  *scores++ = ((pass == 0 && declare_simd_cnt != -1)
11140 		       ? codes.length () - 1 : codes.length ());
11141 	}
11142       return declare_simd_cnt == -1 ? 1 : 2;
11143     }
11144   if (matched == nconstructs)
11145     return simd_seen ? -1 : 1;
11146   return 0;
11147 }
11148 
11149 /* Gimplify OACC_CACHE.  */
11150 
11151 static void
gimplify_oacc_cache(tree * expr_p,gimple_seq * pre_p)11152 gimplify_oacc_cache (tree *expr_p, gimple_seq *pre_p)
11153 {
11154   tree expr = *expr_p;
11155 
11156   gimplify_scan_omp_clauses (&OACC_CACHE_CLAUSES (expr), pre_p, ORT_ACC,
11157 			     OACC_CACHE);
11158   gimplify_adjust_omp_clauses (pre_p, NULL, &OACC_CACHE_CLAUSES (expr),
11159 			       OACC_CACHE);
11160 
11161   /* TODO: Do something sensible with this information.  */
11162 
11163   *expr_p = NULL_TREE;
11164 }
11165 
11166 /* Helper function of gimplify_oacc_declare.  The helper's purpose is to,
11167    if required, translate 'kind' in CLAUSE into an 'entry' kind and 'exit'
11168    kind.  The entry kind will replace the one in CLAUSE, while the exit
11169    kind will be used in a new omp_clause and returned to the caller.  */
11170 
11171 static tree
gimplify_oacc_declare_1(tree clause)11172 gimplify_oacc_declare_1 (tree clause)
11173 {
11174   HOST_WIDE_INT kind, new_op;
11175   bool ret = false;
11176   tree c = NULL;
11177 
11178   kind = OMP_CLAUSE_MAP_KIND (clause);
11179 
11180   switch (kind)
11181     {
11182       case GOMP_MAP_ALLOC:
11183 	new_op = GOMP_MAP_RELEASE;
11184 	ret = true;
11185 	break;
11186 
11187       case GOMP_MAP_FROM:
11188 	OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_FORCE_ALLOC);
11189 	new_op = GOMP_MAP_FROM;
11190 	ret = true;
11191 	break;
11192 
11193       case GOMP_MAP_TOFROM:
11194 	OMP_CLAUSE_SET_MAP_KIND (clause, GOMP_MAP_TO);
11195 	new_op = GOMP_MAP_FROM;
11196 	ret = true;
11197 	break;
11198 
11199       case GOMP_MAP_DEVICE_RESIDENT:
11200       case GOMP_MAP_FORCE_DEVICEPTR:
11201       case GOMP_MAP_FORCE_PRESENT:
11202       case GOMP_MAP_LINK:
11203       case GOMP_MAP_POINTER:
11204       case GOMP_MAP_TO:
11205 	break;
11206 
11207       default:
11208 	gcc_unreachable ();
11209 	break;
11210     }
11211 
11212   if (ret)
11213     {
11214       c = build_omp_clause (OMP_CLAUSE_LOCATION (clause), OMP_CLAUSE_MAP);
11215       OMP_CLAUSE_SET_MAP_KIND (c, new_op);
11216       OMP_CLAUSE_DECL (c) = OMP_CLAUSE_DECL (clause);
11217     }
11218 
11219   return c;
11220 }
11221 
11222 /* Gimplify OACC_DECLARE.  */
11223 
11224 static void
gimplify_oacc_declare(tree * expr_p,gimple_seq * pre_p)11225 gimplify_oacc_declare (tree *expr_p, gimple_seq *pre_p)
11226 {
11227   tree expr = *expr_p;
11228   gomp_target *stmt;
11229   tree clauses, t, decl;
11230 
11231   clauses = OACC_DECLARE_CLAUSES (expr);
11232 
11233   gimplify_scan_omp_clauses (&clauses, pre_p, ORT_TARGET_DATA, OACC_DECLARE);
11234   gimplify_adjust_omp_clauses (pre_p, NULL, &clauses, OACC_DECLARE);
11235 
11236   for (t = clauses; t; t = OMP_CLAUSE_CHAIN (t))
11237     {
11238       decl = OMP_CLAUSE_DECL (t);
11239 
11240       if (TREE_CODE (decl) == MEM_REF)
11241 	decl = TREE_OPERAND (decl, 0);
11242 
11243       if (VAR_P (decl) && !is_oacc_declared (decl))
11244 	{
11245 	  tree attr = get_identifier ("oacc declare target");
11246 	  DECL_ATTRIBUTES (decl) = tree_cons (attr, NULL_TREE,
11247 					      DECL_ATTRIBUTES (decl));
11248 	}
11249 
11250       if (VAR_P (decl)
11251 	  && !is_global_var (decl)
11252 	  && DECL_CONTEXT (decl) == current_function_decl)
11253 	{
11254 	  tree c = gimplify_oacc_declare_1 (t);
11255 	  if (c)
11256 	    {
11257 	      if (oacc_declare_returns == NULL)
11258 		oacc_declare_returns = new hash_map<tree, tree>;
11259 
11260 	      oacc_declare_returns->put (decl, c);
11261 	    }
11262 	}
11263 
11264       if (gimplify_omp_ctxp)
11265 	omp_add_variable (gimplify_omp_ctxp, decl, GOVD_SEEN);
11266     }
11267 
11268   stmt = gimple_build_omp_target (NULL, GF_OMP_TARGET_KIND_OACC_DECLARE,
11269 				  clauses);
11270 
11271   gimplify_seq_add_stmt (pre_p, stmt);
11272 
11273   *expr_p = NULL_TREE;
11274 }
11275 
11276 /* Gimplify the contents of an OMP_PARALLEL statement.  This involves
11277    gimplification of the body, as well as scanning the body for used
11278    variables.  We need to do this scan now, because variable-sized
11279    decls will be decomposed during gimplification.  */
11280 
11281 static void
gimplify_omp_parallel(tree * expr_p,gimple_seq * pre_p)11282 gimplify_omp_parallel (tree *expr_p, gimple_seq *pre_p)
11283 {
11284   tree expr = *expr_p;
11285   gimple *g;
11286   gimple_seq body = NULL;
11287 
11288   gimplify_scan_omp_clauses (&OMP_PARALLEL_CLAUSES (expr), pre_p,
11289 			     OMP_PARALLEL_COMBINED (expr)
11290 			     ? ORT_COMBINED_PARALLEL
11291 			     : ORT_PARALLEL, OMP_PARALLEL);
11292 
11293   push_gimplify_context ();
11294 
11295   g = gimplify_and_return_first (OMP_PARALLEL_BODY (expr), &body);
11296   if (gimple_code (g) == GIMPLE_BIND)
11297     pop_gimplify_context (g);
11298   else
11299     pop_gimplify_context (NULL);
11300 
11301   gimplify_adjust_omp_clauses (pre_p, body, &OMP_PARALLEL_CLAUSES (expr),
11302 			       OMP_PARALLEL);
11303 
11304   g = gimple_build_omp_parallel (body,
11305 				 OMP_PARALLEL_CLAUSES (expr),
11306 				 NULL_TREE, NULL_TREE);
11307   if (OMP_PARALLEL_COMBINED (expr))
11308     gimple_omp_set_subcode (g, GF_OMP_PARALLEL_COMBINED);
11309   gimplify_seq_add_stmt (pre_p, g);
11310   *expr_p = NULL_TREE;
11311 }
11312 
11313 /* Gimplify the contents of an OMP_TASK statement.  This involves
11314    gimplification of the body, as well as scanning the body for used
11315    variables.  We need to do this scan now, because variable-sized
11316    decls will be decomposed during gimplification.  */
11317 
11318 static void
gimplify_omp_task(tree * expr_p,gimple_seq * pre_p)11319 gimplify_omp_task (tree *expr_p, gimple_seq *pre_p)
11320 {
11321   tree expr = *expr_p;
11322   gimple *g;
11323   gimple_seq body = NULL;
11324 
11325   if (OMP_TASK_BODY (expr) == NULL_TREE)
11326     for (tree c = OMP_TASK_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
11327       if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
11328 	  && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_MUTEXINOUTSET)
11329 	{
11330 	  error_at (OMP_CLAUSE_LOCATION (c),
11331 		    "%<mutexinoutset%> kind in %<depend%> clause on a "
11332 		    "%<taskwait%> construct");
11333 	  break;
11334 	}
11335 
11336   gimplify_scan_omp_clauses (&OMP_TASK_CLAUSES (expr), pre_p,
11337 			     omp_find_clause (OMP_TASK_CLAUSES (expr),
11338 					      OMP_CLAUSE_UNTIED)
11339 			     ? ORT_UNTIED_TASK : ORT_TASK, OMP_TASK);
11340 
11341   if (OMP_TASK_BODY (expr))
11342     {
11343       push_gimplify_context ();
11344 
11345       g = gimplify_and_return_first (OMP_TASK_BODY (expr), &body);
11346       if (gimple_code (g) == GIMPLE_BIND)
11347 	pop_gimplify_context (g);
11348       else
11349 	pop_gimplify_context (NULL);
11350     }
11351 
11352   gimplify_adjust_omp_clauses (pre_p, body, &OMP_TASK_CLAUSES (expr),
11353 			       OMP_TASK);
11354 
11355   g = gimple_build_omp_task (body,
11356 			     OMP_TASK_CLAUSES (expr),
11357 			     NULL_TREE, NULL_TREE,
11358 			     NULL_TREE, NULL_TREE, NULL_TREE);
11359   if (OMP_TASK_BODY (expr) == NULL_TREE)
11360     gimple_omp_task_set_taskwait_p (g, true);
11361   gimplify_seq_add_stmt (pre_p, g);
11362   *expr_p = NULL_TREE;
11363 }
11364 
11365 /* Helper function for gimplify_omp_for.  If *TP is not a gimple constant,
11366    force it into a temporary initialized in PRE_P and add firstprivate clause
11367    to ORIG_FOR_STMT.  */
11368 
11369 static void
gimplify_omp_taskloop_expr(tree type,tree * tp,gimple_seq * pre_p,tree orig_for_stmt)11370 gimplify_omp_taskloop_expr (tree type, tree *tp, gimple_seq *pre_p,
11371 			    tree orig_for_stmt)
11372 {
11373   if (*tp == NULL || is_gimple_constant (*tp))
11374     return;
11375 
11376   *tp = get_initialized_tmp_var (*tp, pre_p, NULL, false);
11377   /* Reference to pointer conversion is considered useless,
11378      but is significant for firstprivate clause.  Force it
11379      here.  */
11380   if (type
11381       && TREE_CODE (type) == POINTER_TYPE
11382       && TREE_CODE (TREE_TYPE (*tp)) == REFERENCE_TYPE)
11383     {
11384       tree v = create_tmp_var (TYPE_MAIN_VARIANT (type));
11385       tree m = build2 (INIT_EXPR, TREE_TYPE (v), v, *tp);
11386       gimplify_and_add (m, pre_p);
11387       *tp = v;
11388     }
11389 
11390   tree c = build_omp_clause (input_location, OMP_CLAUSE_FIRSTPRIVATE);
11391   OMP_CLAUSE_DECL (c) = *tp;
11392   OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (orig_for_stmt);
11393   OMP_FOR_CLAUSES (orig_for_stmt) = c;
11394 }
11395 
11396 /* Gimplify the gross structure of an OMP_FOR statement.  */
11397 
11398 static enum gimplify_status
gimplify_omp_for(tree * expr_p,gimple_seq * pre_p)11399 gimplify_omp_for (tree *expr_p, gimple_seq *pre_p)
11400 {
11401   tree for_stmt, orig_for_stmt, inner_for_stmt = NULL_TREE, decl, var, t;
11402   enum gimplify_status ret = GS_ALL_DONE;
11403   enum gimplify_status tret;
11404   gomp_for *gfor;
11405   gimple_seq for_body, for_pre_body;
11406   int i;
11407   bitmap has_decl_expr = NULL;
11408   enum omp_region_type ort = ORT_WORKSHARE;
11409   bool openacc = TREE_CODE (*expr_p) == OACC_LOOP;
11410 
11411   orig_for_stmt = for_stmt = *expr_p;
11412 
11413   bool loop_p = (omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_BIND)
11414 		 != NULL_TREE);
11415   if (OMP_FOR_INIT (for_stmt) == NULL_TREE)
11416     {
11417       tree *data[4] = { NULL, NULL, NULL, NULL };
11418       gcc_assert (TREE_CODE (for_stmt) != OACC_LOOP);
11419       inner_for_stmt = walk_tree (&OMP_FOR_BODY (for_stmt),
11420 				  find_combined_omp_for, data, NULL);
11421       if (inner_for_stmt == NULL_TREE)
11422 	{
11423 	  gcc_assert (seen_error ());
11424 	  *expr_p = NULL_TREE;
11425 	  return GS_ERROR;
11426 	}
11427       if (data[2] && OMP_FOR_PRE_BODY (*data[2]))
11428 	{
11429 	  append_to_statement_list_force (OMP_FOR_PRE_BODY (*data[2]),
11430 					  &OMP_FOR_PRE_BODY (for_stmt));
11431 	  OMP_FOR_PRE_BODY (*data[2]) = NULL_TREE;
11432 	}
11433       if (OMP_FOR_PRE_BODY (inner_for_stmt))
11434 	{
11435 	  append_to_statement_list_force (OMP_FOR_PRE_BODY (inner_for_stmt),
11436 					  &OMP_FOR_PRE_BODY (for_stmt));
11437 	  OMP_FOR_PRE_BODY (inner_for_stmt) = NULL_TREE;
11438 	}
11439 
11440       if (data[0])
11441 	{
11442 	  /* We have some statements or variable declarations in between
11443 	     the composite construct directives.  Move them around the
11444 	     inner_for_stmt.  */
11445 	  data[0] = expr_p;
11446 	  for (i = 0; i < 3; i++)
11447 	    if (data[i])
11448 	      {
11449 		tree t = *data[i];
11450 		if (i < 2 && data[i + 1] == &OMP_BODY (t))
11451 		  data[i + 1] = data[i];
11452 		*data[i] = OMP_BODY (t);
11453 		tree body = build3 (BIND_EXPR, void_type_node, NULL_TREE,
11454 				    NULL_TREE, make_node (BLOCK));
11455 		OMP_BODY (t) = body;
11456 		append_to_statement_list_force (inner_for_stmt,
11457 						&BIND_EXPR_BODY (body));
11458 		*data[3] = t;
11459 		data[3] = tsi_stmt_ptr (tsi_start (BIND_EXPR_BODY (body)));
11460 		gcc_assert (*data[3] == inner_for_stmt);
11461 	      }
11462 	  return GS_OK;
11463 	}
11464 
11465       for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (inner_for_stmt)); i++)
11466 	if (!loop_p
11467 	    && OMP_FOR_ORIG_DECLS (inner_for_stmt)
11468 	    && TREE_CODE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt),
11469 					i)) == TREE_LIST
11470 	    && TREE_PURPOSE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt),
11471 					   i)))
11472 	  {
11473 	    tree orig = TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt), i);
11474 	    /* Class iterators aren't allowed on OMP_SIMD, so the only
11475 	       case we need to solve is distribute parallel for.  They are
11476 	       allowed on the loop construct, but that is already handled
11477 	       in gimplify_omp_loop.  */
11478 	    gcc_assert (TREE_CODE (inner_for_stmt) == OMP_FOR
11479 			&& TREE_CODE (for_stmt) == OMP_DISTRIBUTE
11480 			&& data[1]);
11481 	    tree orig_decl = TREE_PURPOSE (orig);
11482 	    tree last = TREE_VALUE (orig);
11483 	    tree *pc;
11484 	    for (pc = &OMP_FOR_CLAUSES (inner_for_stmt);
11485 		 *pc; pc = &OMP_CLAUSE_CHAIN (*pc))
11486 	      if ((OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_PRIVATE
11487 		   || OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_LASTPRIVATE)
11488 		  && OMP_CLAUSE_DECL (*pc) == orig_decl)
11489 		break;
11490 	    if (*pc == NULL_TREE)
11491 	      {
11492 		tree *spc;
11493 		for (spc = &OMP_PARALLEL_CLAUSES (*data[1]);
11494 		     *spc; spc = &OMP_CLAUSE_CHAIN (*spc))
11495 		  if (OMP_CLAUSE_CODE (*spc) == OMP_CLAUSE_PRIVATE
11496 		      && OMP_CLAUSE_DECL (*spc) == orig_decl)
11497 		    break;
11498 		if (*spc)
11499 		  {
11500 		    tree c = *spc;
11501 		    *spc = OMP_CLAUSE_CHAIN (c);
11502 		    OMP_CLAUSE_CHAIN (c) = NULL_TREE;
11503 		    *pc = c;
11504 		  }
11505 	      }
11506 	    if (*pc == NULL_TREE)
11507 	      ;
11508 	    else if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_PRIVATE)
11509 	      {
11510 		/* private clause will appear only on inner_for_stmt.
11511 		   Change it into firstprivate, and add private clause
11512 		   on for_stmt.  */
11513 		tree c = copy_node (*pc);
11514 		OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (for_stmt);
11515 		OMP_FOR_CLAUSES (for_stmt) = c;
11516 		OMP_CLAUSE_CODE (*pc) = OMP_CLAUSE_FIRSTPRIVATE;
11517 		lang_hooks.decls.omp_finish_clause (*pc, pre_p, openacc);
11518 	      }
11519 	    else
11520 	      {
11521 		/* lastprivate clause will appear on both inner_for_stmt
11522 		   and for_stmt.  Add firstprivate clause to
11523 		   inner_for_stmt.  */
11524 		tree c = build_omp_clause (OMP_CLAUSE_LOCATION (*pc),
11525 					   OMP_CLAUSE_FIRSTPRIVATE);
11526 		OMP_CLAUSE_DECL (c) = OMP_CLAUSE_DECL (*pc);
11527 		OMP_CLAUSE_CHAIN (c) = *pc;
11528 		*pc = c;
11529 		lang_hooks.decls.omp_finish_clause (*pc, pre_p, openacc);
11530 	      }
11531 	    tree c = build_omp_clause (UNKNOWN_LOCATION,
11532 				       OMP_CLAUSE_FIRSTPRIVATE);
11533 	    OMP_CLAUSE_DECL (c) = last;
11534 	    OMP_CLAUSE_CHAIN (c) = OMP_PARALLEL_CLAUSES (*data[1]);
11535 	    OMP_PARALLEL_CLAUSES (*data[1]) = c;
11536 	    c = build_omp_clause (UNKNOWN_LOCATION,
11537 				  *pc ? OMP_CLAUSE_SHARED
11538 				      : OMP_CLAUSE_FIRSTPRIVATE);
11539 	    OMP_CLAUSE_DECL (c) = orig_decl;
11540 	    OMP_CLAUSE_CHAIN (c) = OMP_PARALLEL_CLAUSES (*data[1]);
11541 	    OMP_PARALLEL_CLAUSES (*data[1]) = c;
11542 	  }
11543       /* Similarly, take care of C++ range for temporaries, those should
11544 	 be firstprivate on OMP_PARALLEL if any.  */
11545       if (data[1])
11546 	for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (inner_for_stmt)); i++)
11547 	  if (OMP_FOR_ORIG_DECLS (inner_for_stmt)
11548 	      && TREE_CODE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt),
11549 					  i)) == TREE_LIST
11550 	      && TREE_CHAIN (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt),
11551 					   i)))
11552 	    {
11553 	      tree orig
11554 		= TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (inner_for_stmt), i);
11555 	      tree v = TREE_CHAIN (orig);
11556 	      tree c = build_omp_clause (UNKNOWN_LOCATION,
11557 					 OMP_CLAUSE_FIRSTPRIVATE);
11558 	      /* First add firstprivate clause for the __for_end artificial
11559 		 decl.  */
11560 	      OMP_CLAUSE_DECL (c) = TREE_VEC_ELT (v, 1);
11561 	      if (TREE_CODE (TREE_TYPE (OMP_CLAUSE_DECL (c)))
11562 		  == REFERENCE_TYPE)
11563 		OMP_CLAUSE_FIRSTPRIVATE_NO_REFERENCE (c) = 1;
11564 	      OMP_CLAUSE_CHAIN (c) = OMP_PARALLEL_CLAUSES (*data[1]);
11565 	      OMP_PARALLEL_CLAUSES (*data[1]) = c;
11566 	      if (TREE_VEC_ELT (v, 0))
11567 		{
11568 		  /* And now the same for __for_range artificial decl if it
11569 		     exists.  */
11570 		  c = build_omp_clause (UNKNOWN_LOCATION,
11571 					OMP_CLAUSE_FIRSTPRIVATE);
11572 		  OMP_CLAUSE_DECL (c) = TREE_VEC_ELT (v, 0);
11573 		  if (TREE_CODE (TREE_TYPE (OMP_CLAUSE_DECL (c)))
11574 		      == REFERENCE_TYPE)
11575 		    OMP_CLAUSE_FIRSTPRIVATE_NO_REFERENCE (c) = 1;
11576 		  OMP_CLAUSE_CHAIN (c) = OMP_PARALLEL_CLAUSES (*data[1]);
11577 		  OMP_PARALLEL_CLAUSES (*data[1]) = c;
11578 		}
11579 	    }
11580     }
11581 
11582   switch (TREE_CODE (for_stmt))
11583     {
11584     case OMP_FOR:
11585       if (OMP_FOR_NON_RECTANGULAR (inner_for_stmt ? inner_for_stmt : for_stmt))
11586 	{
11587 	  if (omp_find_clause (OMP_FOR_CLAUSES (for_stmt),
11588 			       OMP_CLAUSE_SCHEDULE))
11589 	    error_at (EXPR_LOCATION (for_stmt),
11590 		      "%qs clause may not appear on non-rectangular %qs",
11591 		      "schedule", "for");
11592 	  if (omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_ORDERED))
11593 	    error_at (EXPR_LOCATION (for_stmt),
11594 		      "%qs clause may not appear on non-rectangular %qs",
11595 		      "ordered", "for");
11596 	}
11597       break;
11598     case OMP_DISTRIBUTE:
11599       if (OMP_FOR_NON_RECTANGULAR (inner_for_stmt ? inner_for_stmt : for_stmt)
11600 	  && omp_find_clause (OMP_FOR_CLAUSES (for_stmt),
11601 			      OMP_CLAUSE_DIST_SCHEDULE))
11602 	error_at (EXPR_LOCATION (for_stmt),
11603 		  "%qs clause may not appear on non-rectangular %qs",
11604 		  "dist_schedule", "distribute");
11605       break;
11606     case OACC_LOOP:
11607       ort = ORT_ACC;
11608       break;
11609     case OMP_TASKLOOP:
11610       if (omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_UNTIED))
11611 	ort = ORT_UNTIED_TASKLOOP;
11612       else
11613 	ort = ORT_TASKLOOP;
11614       break;
11615     case OMP_SIMD:
11616       ort = ORT_SIMD;
11617       break;
11618     default:
11619       gcc_unreachable ();
11620     }
11621 
11622   /* Set OMP_CLAUSE_LINEAR_NO_COPYIN flag on explicit linear
11623      clause for the IV.  */
11624   if (ort == ORT_SIMD && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
11625     {
11626       t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), 0);
11627       gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
11628       decl = TREE_OPERAND (t, 0);
11629       for (tree c = OMP_FOR_CLAUSES (for_stmt); c; c = OMP_CLAUSE_CHAIN (c))
11630 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
11631 	    && OMP_CLAUSE_DECL (c) == decl)
11632 	  {
11633 	    OMP_CLAUSE_LINEAR_NO_COPYIN (c) = 1;
11634 	    break;
11635 	  }
11636     }
11637 
11638   if (TREE_CODE (for_stmt) != OMP_TASKLOOP)
11639     gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (for_stmt), pre_p, ort,
11640 			       loop_p && TREE_CODE (for_stmt) != OMP_SIMD
11641 			       ? OMP_LOOP : TREE_CODE (for_stmt));
11642 
11643   if (TREE_CODE (for_stmt) == OMP_DISTRIBUTE)
11644     gimplify_omp_ctxp->distribute = true;
11645 
11646   /* Handle OMP_FOR_INIT.  */
11647   for_pre_body = NULL;
11648   if ((ort == ORT_SIMD
11649        || (inner_for_stmt && TREE_CODE (inner_for_stmt) == OMP_SIMD))
11650       && OMP_FOR_PRE_BODY (for_stmt))
11651     {
11652       has_decl_expr = BITMAP_ALLOC (NULL);
11653       if (TREE_CODE (OMP_FOR_PRE_BODY (for_stmt)) == DECL_EXPR
11654 	  && TREE_CODE (DECL_EXPR_DECL (OMP_FOR_PRE_BODY (for_stmt)))
11655 	     == VAR_DECL)
11656 	{
11657 	  t = OMP_FOR_PRE_BODY (for_stmt);
11658 	  bitmap_set_bit (has_decl_expr, DECL_UID (DECL_EXPR_DECL (t)));
11659 	}
11660       else if (TREE_CODE (OMP_FOR_PRE_BODY (for_stmt)) == STATEMENT_LIST)
11661 	{
11662 	  tree_stmt_iterator si;
11663 	  for (si = tsi_start (OMP_FOR_PRE_BODY (for_stmt)); !tsi_end_p (si);
11664 	       tsi_next (&si))
11665 	    {
11666 	      t = tsi_stmt (si);
11667 	      if (TREE_CODE (t) == DECL_EXPR
11668 		  && TREE_CODE (DECL_EXPR_DECL (t)) == VAR_DECL)
11669 		bitmap_set_bit (has_decl_expr, DECL_UID (DECL_EXPR_DECL (t)));
11670 	    }
11671 	}
11672     }
11673   if (OMP_FOR_PRE_BODY (for_stmt))
11674     {
11675       if (TREE_CODE (for_stmt) != OMP_TASKLOOP || gimplify_omp_ctxp)
11676 	gimplify_and_add (OMP_FOR_PRE_BODY (for_stmt), &for_pre_body);
11677       else
11678 	{
11679 	  struct gimplify_omp_ctx ctx;
11680 	  memset (&ctx, 0, sizeof (ctx));
11681 	  ctx.region_type = ORT_NONE;
11682 	  gimplify_omp_ctxp = &ctx;
11683 	  gimplify_and_add (OMP_FOR_PRE_BODY (for_stmt), &for_pre_body);
11684 	  gimplify_omp_ctxp = NULL;
11685 	}
11686     }
11687   OMP_FOR_PRE_BODY (for_stmt) = NULL_TREE;
11688 
11689   if (OMP_FOR_INIT (for_stmt) == NULL_TREE)
11690     for_stmt = inner_for_stmt;
11691 
11692   /* For taskloop, need to gimplify the start, end and step before the
11693      taskloop, outside of the taskloop omp context.  */
11694   if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
11695     {
11696       for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
11697 	{
11698 	  t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
11699 	  gimple_seq *for_pre_p = (gimple_seq_empty_p (for_pre_body)
11700 				   ? pre_p : &for_pre_body);
11701 	      tree type = TREE_TYPE (TREE_OPERAND (t, 0));
11702 	  if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC)
11703 	    {
11704 	      tree v = TREE_OPERAND (t, 1);
11705 	      gimplify_omp_taskloop_expr (type, &TREE_VEC_ELT (v, 1),
11706 					  for_pre_p, orig_for_stmt);
11707 	      gimplify_omp_taskloop_expr (type, &TREE_VEC_ELT (v, 2),
11708 					  for_pre_p, orig_for_stmt);
11709 	    }
11710 	  else
11711 	    gimplify_omp_taskloop_expr (type, &TREE_OPERAND (t, 1), for_pre_p,
11712 					orig_for_stmt);
11713 
11714 	  /* Handle OMP_FOR_COND.  */
11715 	  t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
11716 	  if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC)
11717 	    {
11718 	      tree v = TREE_OPERAND (t, 1);
11719 	      gimplify_omp_taskloop_expr (type, &TREE_VEC_ELT (v, 1),
11720 					  for_pre_p, orig_for_stmt);
11721 	      gimplify_omp_taskloop_expr (type, &TREE_VEC_ELT (v, 2),
11722 					  for_pre_p, orig_for_stmt);
11723 	    }
11724 	  else
11725 	    gimplify_omp_taskloop_expr (type, &TREE_OPERAND (t, 1), for_pre_p,
11726 					orig_for_stmt);
11727 
11728 	  /* Handle OMP_FOR_INCR.  */
11729 	  t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
11730 	  if (TREE_CODE (t) == MODIFY_EXPR)
11731 	    {
11732 	      decl = TREE_OPERAND (t, 0);
11733 	      t = TREE_OPERAND (t, 1);
11734 	      tree *tp = &TREE_OPERAND (t, 1);
11735 	      if (TREE_CODE (t) == PLUS_EXPR && *tp == decl)
11736 		tp = &TREE_OPERAND (t, 0);
11737 
11738 	      gimplify_omp_taskloop_expr (NULL_TREE, tp, for_pre_p,
11739 					  orig_for_stmt);
11740 	    }
11741 	}
11742 
11743       gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (orig_for_stmt), pre_p, ort,
11744 				 OMP_TASKLOOP);
11745     }
11746 
11747   if (orig_for_stmt != for_stmt)
11748     gimplify_omp_ctxp->combined_loop = true;
11749 
11750   for_body = NULL;
11751   gcc_assert (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
11752 	      == TREE_VEC_LENGTH (OMP_FOR_COND (for_stmt)));
11753   gcc_assert (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
11754 	      == TREE_VEC_LENGTH (OMP_FOR_INCR (for_stmt)));
11755 
11756   tree c = omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_ORDERED);
11757   bool is_doacross = false;
11758   if (c && OMP_CLAUSE_ORDERED_EXPR (c))
11759     {
11760       is_doacross = true;
11761       gimplify_omp_ctxp->loop_iter_var.create (TREE_VEC_LENGTH
11762 						 (OMP_FOR_INIT (for_stmt))
11763 					       * 2);
11764     }
11765   int collapse = 1, tile = 0;
11766   c = omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_COLLAPSE);
11767   if (c)
11768     collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (c));
11769   c = omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_TILE);
11770   if (c)
11771     tile = list_length (OMP_CLAUSE_TILE_LIST (c));
11772   c = omp_find_clause (OMP_FOR_CLAUSES (for_stmt), OMP_CLAUSE_ALLOCATE);
11773   hash_set<tree> *allocate_uids = NULL;
11774   if (c)
11775     {
11776       allocate_uids = new hash_set<tree>;
11777       for (; c; c = OMP_CLAUSE_CHAIN (c))
11778 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_ALLOCATE)
11779 	  allocate_uids->add (OMP_CLAUSE_DECL (c));
11780     }
11781   for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
11782     {
11783       t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
11784       gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
11785       decl = TREE_OPERAND (t, 0);
11786       gcc_assert (DECL_P (decl));
11787       gcc_assert (INTEGRAL_TYPE_P (TREE_TYPE (decl))
11788 		  || POINTER_TYPE_P (TREE_TYPE (decl)));
11789       if (is_doacross)
11790 	{
11791 	  if (TREE_CODE (for_stmt) == OMP_FOR && OMP_FOR_ORIG_DECLS (for_stmt))
11792 	    {
11793 	      tree orig_decl = TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i);
11794 	      if (TREE_CODE (orig_decl) == TREE_LIST)
11795 		{
11796 		  orig_decl = TREE_PURPOSE (orig_decl);
11797 		  if (!orig_decl)
11798 		    orig_decl = decl;
11799 		}
11800 	      gimplify_omp_ctxp->loop_iter_var.quick_push (orig_decl);
11801 	    }
11802 	  else
11803 	    gimplify_omp_ctxp->loop_iter_var.quick_push (decl);
11804 	  gimplify_omp_ctxp->loop_iter_var.quick_push (decl);
11805 	}
11806 
11807       /* Make sure the iteration variable is private.  */
11808       tree c = NULL_TREE;
11809       tree c2 = NULL_TREE;
11810       if (orig_for_stmt != for_stmt)
11811 	{
11812 	  /* Preserve this information until we gimplify the inner simd.  */
11813 	  if (has_decl_expr
11814 	      && bitmap_bit_p (has_decl_expr, DECL_UID (decl)))
11815 	    TREE_PRIVATE (t) = 1;
11816 	}
11817       else if (ort == ORT_SIMD)
11818 	{
11819 	  splay_tree_node n = splay_tree_lookup (gimplify_omp_ctxp->variables,
11820 						 (splay_tree_key) decl);
11821 	  omp_is_private (gimplify_omp_ctxp, decl,
11822 			  1 + (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt))
11823 			       != 1));
11824 	  if (n != NULL && (n->value & GOVD_DATA_SHARE_CLASS) != 0)
11825 	    {
11826 	      omp_notice_variable (gimplify_omp_ctxp, decl, true);
11827 	      if (n->value & GOVD_LASTPRIVATE_CONDITIONAL)
11828 		for (tree c3 = omp_find_clause (OMP_FOR_CLAUSES (for_stmt),
11829 						OMP_CLAUSE_LASTPRIVATE);
11830 		     c3; c3 = omp_find_clause (OMP_CLAUSE_CHAIN (c3),
11831 					       OMP_CLAUSE_LASTPRIVATE))
11832 		  if (OMP_CLAUSE_DECL (c3) == decl)
11833 		    {
11834 		      warning_at (OMP_CLAUSE_LOCATION (c3), 0,
11835 				  "conditional %<lastprivate%> on loop "
11836 				  "iterator %qD ignored", decl);
11837 		      OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c3) = 0;
11838 		      n->value &= ~GOVD_LASTPRIVATE_CONDITIONAL;
11839 		    }
11840 	    }
11841 	  else if (TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1 && !loop_p)
11842 	    {
11843 	      c = build_omp_clause (input_location, OMP_CLAUSE_LINEAR);
11844 	      OMP_CLAUSE_LINEAR_NO_COPYIN (c) = 1;
11845 	      unsigned int flags = GOVD_LINEAR | GOVD_EXPLICIT | GOVD_SEEN;
11846 	      if ((has_decl_expr
11847 		   && bitmap_bit_p (has_decl_expr, DECL_UID (decl)))
11848 		  || TREE_PRIVATE (t))
11849 		{
11850 		  OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
11851 		  flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
11852 		}
11853 	      struct gimplify_omp_ctx *outer
11854 		= gimplify_omp_ctxp->outer_context;
11855 	      if (outer && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
11856 		{
11857 		  if (outer->region_type == ORT_WORKSHARE
11858 		      && outer->combined_loop)
11859 		    {
11860 		      n = splay_tree_lookup (outer->variables,
11861 					     (splay_tree_key)decl);
11862 		      if (n != NULL && (n->value & GOVD_LOCAL) != 0)
11863 			{
11864 			  OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
11865 			  flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
11866 			}
11867 		      else
11868 			{
11869 			  struct gimplify_omp_ctx *octx = outer->outer_context;
11870 			  if (octx
11871 			      && octx->region_type == ORT_COMBINED_PARALLEL
11872 			      && octx->outer_context
11873 			      && (octx->outer_context->region_type
11874 				  == ORT_WORKSHARE)
11875 			      && octx->outer_context->combined_loop)
11876 			    {
11877 			      octx = octx->outer_context;
11878 			      n = splay_tree_lookup (octx->variables,
11879 						     (splay_tree_key)decl);
11880 			      if (n != NULL && (n->value & GOVD_LOCAL) != 0)
11881 				{
11882 				  OMP_CLAUSE_LINEAR_NO_COPYOUT (c) = 1;
11883 				  flags |= GOVD_LINEAR_LASTPRIVATE_NO_OUTER;
11884 				}
11885 			    }
11886 			}
11887 		    }
11888 		}
11889 
11890 	      OMP_CLAUSE_DECL (c) = decl;
11891 	      OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (for_stmt);
11892 	      OMP_FOR_CLAUSES (for_stmt) = c;
11893 	      omp_add_variable (gimplify_omp_ctxp, decl, flags);
11894 	      if (outer && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c))
11895 		{
11896 		  if (outer->region_type == ORT_WORKSHARE
11897 		      && outer->combined_loop)
11898 		    {
11899 		      if (outer->outer_context
11900 			  && (outer->outer_context->region_type
11901 			      == ORT_COMBINED_PARALLEL))
11902 			outer = outer->outer_context;
11903 		      else if (omp_check_private (outer, decl, false))
11904 			outer = NULL;
11905 		    }
11906 		  else if (((outer->region_type & ORT_TASKLOOP)
11907 			    == ORT_TASKLOOP)
11908 			   && outer->combined_loop
11909 			   && !omp_check_private (gimplify_omp_ctxp,
11910 						  decl, false))
11911 		    ;
11912 		  else if (outer->region_type != ORT_COMBINED_PARALLEL)
11913 		    {
11914 		      omp_notice_variable (outer, decl, true);
11915 		      outer = NULL;
11916 		    }
11917 		  if (outer)
11918 		    {
11919 		      n = splay_tree_lookup (outer->variables,
11920 					     (splay_tree_key)decl);
11921 		      if (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
11922 			{
11923 			  omp_add_variable (outer, decl,
11924 					    GOVD_LASTPRIVATE | GOVD_SEEN);
11925 			  if (outer->region_type == ORT_COMBINED_PARALLEL
11926 			      && outer->outer_context
11927 			      && (outer->outer_context->region_type
11928 				  == ORT_WORKSHARE)
11929 			      && outer->outer_context->combined_loop)
11930 			    {
11931 			      outer = outer->outer_context;
11932 			      n = splay_tree_lookup (outer->variables,
11933 						     (splay_tree_key)decl);
11934 			      if (omp_check_private (outer, decl, false))
11935 				outer = NULL;
11936 			      else if (n == NULL
11937 				       || ((n->value & GOVD_DATA_SHARE_CLASS)
11938 					   == 0))
11939 				omp_add_variable (outer, decl,
11940 						  GOVD_LASTPRIVATE
11941 						  | GOVD_SEEN);
11942 			      else
11943 				outer = NULL;
11944 			    }
11945 			  if (outer && outer->outer_context
11946 			      && ((outer->outer_context->region_type
11947 				   & ORT_COMBINED_TEAMS) == ORT_COMBINED_TEAMS
11948 				  || (((outer->region_type & ORT_TASKLOOP)
11949 				       == ORT_TASKLOOP)
11950 				      && (outer->outer_context->region_type
11951 					  == ORT_COMBINED_PARALLEL))))
11952 			    {
11953 			      outer = outer->outer_context;
11954 			      n = splay_tree_lookup (outer->variables,
11955 						     (splay_tree_key)decl);
11956 			      if (n == NULL
11957 				  || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
11958 				omp_add_variable (outer, decl,
11959 						  GOVD_SHARED | GOVD_SEEN);
11960 			      else
11961 				outer = NULL;
11962 			    }
11963 			  if (outer && outer->outer_context)
11964 			    omp_notice_variable (outer->outer_context, decl,
11965 						 true);
11966 			}
11967 		    }
11968 		}
11969 	    }
11970 	  else
11971 	    {
11972 	      bool lastprivate
11973 		= (!has_decl_expr
11974 		   || !bitmap_bit_p (has_decl_expr, DECL_UID (decl)));
11975 	      if (TREE_PRIVATE (t))
11976 		lastprivate = false;
11977 	      if (loop_p && OMP_FOR_ORIG_DECLS (for_stmt))
11978 		{
11979 		  tree elt = TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i);
11980 		  if (TREE_CODE (elt) == TREE_LIST && TREE_PURPOSE (elt))
11981 		    lastprivate = false;
11982 		}
11983 
11984 	      struct gimplify_omp_ctx *outer
11985 		= gimplify_omp_ctxp->outer_context;
11986 	      if (outer && lastprivate)
11987 		{
11988 		  if (outer->region_type == ORT_WORKSHARE
11989 		      && outer->combined_loop)
11990 		    {
11991 		      n = splay_tree_lookup (outer->variables,
11992 					     (splay_tree_key)decl);
11993 		      if (n != NULL && (n->value & GOVD_LOCAL) != 0)
11994 			{
11995 			  lastprivate = false;
11996 			  outer = NULL;
11997 			}
11998 		      else if (outer->outer_context
11999 			       && (outer->outer_context->region_type
12000 				   == ORT_COMBINED_PARALLEL))
12001 			outer = outer->outer_context;
12002 		      else if (omp_check_private (outer, decl, false))
12003 			outer = NULL;
12004 		    }
12005 		  else if (((outer->region_type & ORT_TASKLOOP)
12006 			    == ORT_TASKLOOP)
12007 			   && outer->combined_loop
12008 			   && !omp_check_private (gimplify_omp_ctxp,
12009 						  decl, false))
12010 		    ;
12011 		  else if (outer->region_type != ORT_COMBINED_PARALLEL)
12012 		    {
12013 		      omp_notice_variable (outer, decl, true);
12014 		      outer = NULL;
12015 		    }
12016 		  if (outer)
12017 		    {
12018 		      n = splay_tree_lookup (outer->variables,
12019 					     (splay_tree_key)decl);
12020 		      if (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
12021 			{
12022 			  omp_add_variable (outer, decl,
12023 					    GOVD_LASTPRIVATE | GOVD_SEEN);
12024 			  if (outer->region_type == ORT_COMBINED_PARALLEL
12025 			      && outer->outer_context
12026 			      && (outer->outer_context->region_type
12027 				  == ORT_WORKSHARE)
12028 			      && outer->outer_context->combined_loop)
12029 			    {
12030 			      outer = outer->outer_context;
12031 			      n = splay_tree_lookup (outer->variables,
12032 						     (splay_tree_key)decl);
12033 			      if (omp_check_private (outer, decl, false))
12034 				outer = NULL;
12035 			      else if (n == NULL
12036 				       || ((n->value & GOVD_DATA_SHARE_CLASS)
12037 					   == 0))
12038 				omp_add_variable (outer, decl,
12039 						  GOVD_LASTPRIVATE
12040 						  | GOVD_SEEN);
12041 			      else
12042 				outer = NULL;
12043 			    }
12044 			  if (outer && outer->outer_context
12045 			      && ((outer->outer_context->region_type
12046 				   & ORT_COMBINED_TEAMS) == ORT_COMBINED_TEAMS
12047 				  || (((outer->region_type & ORT_TASKLOOP)
12048 				       == ORT_TASKLOOP)
12049 				      && (outer->outer_context->region_type
12050 					  == ORT_COMBINED_PARALLEL))))
12051 			    {
12052 			      outer = outer->outer_context;
12053 			      n = splay_tree_lookup (outer->variables,
12054 						     (splay_tree_key)decl);
12055 			      if (n == NULL
12056 				  || (n->value & GOVD_DATA_SHARE_CLASS) == 0)
12057 				omp_add_variable (outer, decl,
12058 						  GOVD_SHARED | GOVD_SEEN);
12059 			      else
12060 				outer = NULL;
12061 			    }
12062 			  if (outer && outer->outer_context)
12063 			    omp_notice_variable (outer->outer_context, decl,
12064 						 true);
12065 			}
12066 		    }
12067 		}
12068 
12069 	      c = build_omp_clause (input_location,
12070 				    lastprivate ? OMP_CLAUSE_LASTPRIVATE
12071 						: OMP_CLAUSE_PRIVATE);
12072 	      OMP_CLAUSE_DECL (c) = decl;
12073 	      OMP_CLAUSE_CHAIN (c) = OMP_FOR_CLAUSES (for_stmt);
12074 	      OMP_FOR_CLAUSES (for_stmt) = c;
12075 	      omp_add_variable (gimplify_omp_ctxp, decl,
12076 				(lastprivate ? GOVD_LASTPRIVATE : GOVD_PRIVATE)
12077 				| GOVD_EXPLICIT | GOVD_SEEN);
12078 	      c = NULL_TREE;
12079 	    }
12080 	}
12081       else if (omp_is_private (gimplify_omp_ctxp, decl, 0))
12082 	{
12083 	  omp_notice_variable (gimplify_omp_ctxp, decl, true);
12084 	  splay_tree_node n = splay_tree_lookup (gimplify_omp_ctxp->variables,
12085 						 (splay_tree_key) decl);
12086 	  if (n && (n->value & GOVD_LASTPRIVATE_CONDITIONAL))
12087 	    for (tree c3 = omp_find_clause (OMP_FOR_CLAUSES (for_stmt),
12088 					    OMP_CLAUSE_LASTPRIVATE);
12089 		 c3; c3 = omp_find_clause (OMP_CLAUSE_CHAIN (c3),
12090 					   OMP_CLAUSE_LASTPRIVATE))
12091 	      if (OMP_CLAUSE_DECL (c3) == decl)
12092 		{
12093 		  warning_at (OMP_CLAUSE_LOCATION (c3), 0,
12094 			      "conditional %<lastprivate%> on loop "
12095 			      "iterator %qD ignored", decl);
12096 		  OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c3) = 0;
12097 		  n->value &= ~GOVD_LASTPRIVATE_CONDITIONAL;
12098 		}
12099 	}
12100       else
12101 	omp_add_variable (gimplify_omp_ctxp, decl, GOVD_PRIVATE | GOVD_SEEN);
12102 
12103       /* If DECL is not a gimple register, create a temporary variable to act
12104 	 as an iteration counter.  This is valid, since DECL cannot be
12105 	 modified in the body of the loop.  Similarly for any iteration vars
12106 	 in simd with collapse > 1 where the iterator vars must be
12107 	 lastprivate.  And similarly for vars mentioned in allocate clauses.  */
12108       if (orig_for_stmt != for_stmt)
12109 	var = decl;
12110       else if (!is_gimple_reg (decl)
12111 	       || (ort == ORT_SIMD
12112 		   && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) > 1)
12113 	       || (allocate_uids && allocate_uids->contains (decl)))
12114 	{
12115 	  struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
12116 	  /* Make sure omp_add_variable is not called on it prematurely.
12117 	     We call it ourselves a few lines later.  */
12118 	  gimplify_omp_ctxp = NULL;
12119 	  var = create_tmp_var (TREE_TYPE (decl), get_name (decl));
12120 	  gimplify_omp_ctxp = ctx;
12121 	  TREE_OPERAND (t, 0) = var;
12122 
12123 	  gimplify_seq_add_stmt (&for_body, gimple_build_assign (decl, var));
12124 
12125 	  if (ort == ORT_SIMD
12126 	      && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) == 1)
12127 	    {
12128 	      c2 = build_omp_clause (input_location, OMP_CLAUSE_LINEAR);
12129 	      OMP_CLAUSE_LINEAR_NO_COPYIN (c2) = 1;
12130 	      OMP_CLAUSE_LINEAR_NO_COPYOUT (c2) = 1;
12131 	      OMP_CLAUSE_DECL (c2) = var;
12132 	      OMP_CLAUSE_CHAIN (c2) = OMP_FOR_CLAUSES (for_stmt);
12133 	      OMP_FOR_CLAUSES (for_stmt) = c2;
12134 	      omp_add_variable (gimplify_omp_ctxp, var,
12135 				GOVD_LINEAR | GOVD_EXPLICIT | GOVD_SEEN);
12136 	      if (c == NULL_TREE)
12137 		{
12138 		  c = c2;
12139 		  c2 = NULL_TREE;
12140 		}
12141 	    }
12142 	  else
12143 	    omp_add_variable (gimplify_omp_ctxp, var,
12144 			      GOVD_PRIVATE | GOVD_SEEN);
12145 	}
12146       else
12147 	var = decl;
12148 
12149       gimplify_omp_ctxp->in_for_exprs = true;
12150       if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC)
12151 	{
12152 	  tree lb = TREE_OPERAND (t, 1);
12153 	  tret = gimplify_expr (&TREE_VEC_ELT (lb, 1), &for_pre_body, NULL,
12154 				is_gimple_val, fb_rvalue, false);
12155 	  ret = MIN (ret, tret);
12156 	  tret = gimplify_expr (&TREE_VEC_ELT (lb, 2), &for_pre_body, NULL,
12157 				is_gimple_val, fb_rvalue, false);
12158 	}
12159       else
12160 	tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
12161 			      is_gimple_val, fb_rvalue, false);
12162       gimplify_omp_ctxp->in_for_exprs = false;
12163       ret = MIN (ret, tret);
12164       if (ret == GS_ERROR)
12165 	return ret;
12166 
12167       /* Handle OMP_FOR_COND.  */
12168       t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
12169       gcc_assert (COMPARISON_CLASS_P (t));
12170       gcc_assert (TREE_OPERAND (t, 0) == decl);
12171 
12172       gimplify_omp_ctxp->in_for_exprs = true;
12173       if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC)
12174 	{
12175 	  tree ub = TREE_OPERAND (t, 1);
12176 	  tret = gimplify_expr (&TREE_VEC_ELT (ub, 1), &for_pre_body, NULL,
12177 				is_gimple_val, fb_rvalue, false);
12178 	  ret = MIN (ret, tret);
12179 	  tret = gimplify_expr (&TREE_VEC_ELT (ub, 2), &for_pre_body, NULL,
12180 				is_gimple_val, fb_rvalue, false);
12181 	}
12182       else
12183 	tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
12184 			      is_gimple_val, fb_rvalue, false);
12185       gimplify_omp_ctxp->in_for_exprs = false;
12186       ret = MIN (ret, tret);
12187 
12188       /* Handle OMP_FOR_INCR.  */
12189       t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
12190       switch (TREE_CODE (t))
12191 	{
12192 	case PREINCREMENT_EXPR:
12193 	case POSTINCREMENT_EXPR:
12194 	  {
12195 	    tree decl = TREE_OPERAND (t, 0);
12196 	    /* c_omp_for_incr_canonicalize_ptr() should have been
12197 	       called to massage things appropriately.  */
12198 	    gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
12199 
12200 	    if (orig_for_stmt != for_stmt)
12201 	      break;
12202 	    t = build_int_cst (TREE_TYPE (decl), 1);
12203 	    if (c)
12204 	      OMP_CLAUSE_LINEAR_STEP (c) = t;
12205 	    t = build2 (PLUS_EXPR, TREE_TYPE (decl), var, t);
12206 	    t = build2 (MODIFY_EXPR, TREE_TYPE (var), var, t);
12207 	    TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i) = t;
12208 	    break;
12209 	  }
12210 
12211 	case PREDECREMENT_EXPR:
12212 	case POSTDECREMENT_EXPR:
12213 	  /* c_omp_for_incr_canonicalize_ptr() should have been
12214 	     called to massage things appropriately.  */
12215 	  gcc_assert (!POINTER_TYPE_P (TREE_TYPE (decl)));
12216 	  if (orig_for_stmt != for_stmt)
12217 	    break;
12218 	  t = build_int_cst (TREE_TYPE (decl), -1);
12219 	  if (c)
12220 	    OMP_CLAUSE_LINEAR_STEP (c) = t;
12221 	  t = build2 (PLUS_EXPR, TREE_TYPE (decl), var, t);
12222 	  t = build2 (MODIFY_EXPR, TREE_TYPE (var), var, t);
12223 	  TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i) = t;
12224 	  break;
12225 
12226 	case MODIFY_EXPR:
12227 	  gcc_assert (TREE_OPERAND (t, 0) == decl);
12228 	  TREE_OPERAND (t, 0) = var;
12229 
12230 	  t = TREE_OPERAND (t, 1);
12231 	  switch (TREE_CODE (t))
12232 	    {
12233 	    case PLUS_EXPR:
12234 	      if (TREE_OPERAND (t, 1) == decl)
12235 		{
12236 		  TREE_OPERAND (t, 1) = TREE_OPERAND (t, 0);
12237 		  TREE_OPERAND (t, 0) = var;
12238 		  break;
12239 		}
12240 
12241 	      /* Fallthru.  */
12242 	    case MINUS_EXPR:
12243 	    case POINTER_PLUS_EXPR:
12244 	      gcc_assert (TREE_OPERAND (t, 0) == decl);
12245 	      TREE_OPERAND (t, 0) = var;
12246 	      break;
12247 	    default:
12248 	      gcc_unreachable ();
12249 	    }
12250 
12251 	  gimplify_omp_ctxp->in_for_exprs = true;
12252 	  tret = gimplify_expr (&TREE_OPERAND (t, 1), &for_pre_body, NULL,
12253 				is_gimple_val, fb_rvalue, false);
12254 	  ret = MIN (ret, tret);
12255 	  if (c)
12256 	    {
12257 	      tree step = TREE_OPERAND (t, 1);
12258 	      tree stept = TREE_TYPE (decl);
12259 	      if (POINTER_TYPE_P (stept))
12260 		stept = sizetype;
12261 	      step = fold_convert (stept, step);
12262 	      if (TREE_CODE (t) == MINUS_EXPR)
12263 		step = fold_build1 (NEGATE_EXPR, stept, step);
12264 	      OMP_CLAUSE_LINEAR_STEP (c) = step;
12265 	      if (step != TREE_OPERAND (t, 1))
12266 		{
12267 		  tret = gimplify_expr (&OMP_CLAUSE_LINEAR_STEP (c),
12268 					&for_pre_body, NULL,
12269 					is_gimple_val, fb_rvalue, false);
12270 		  ret = MIN (ret, tret);
12271 		}
12272 	    }
12273 	  gimplify_omp_ctxp->in_for_exprs = false;
12274 	  break;
12275 
12276 	default:
12277 	  gcc_unreachable ();
12278 	}
12279 
12280       if (c2)
12281 	{
12282 	  gcc_assert (c);
12283 	  OMP_CLAUSE_LINEAR_STEP (c2) = OMP_CLAUSE_LINEAR_STEP (c);
12284 	}
12285 
12286       if ((var != decl || collapse > 1 || tile) && orig_for_stmt == for_stmt)
12287 	{
12288 	  for (c = OMP_FOR_CLAUSES (for_stmt); c ; c = OMP_CLAUSE_CHAIN (c))
12289 	    if (((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
12290 		  && OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c) == NULL)
12291 		 || (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINEAR
12292 		     && !OMP_CLAUSE_LINEAR_NO_COPYOUT (c)
12293 		     && OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c) == NULL))
12294 		&& OMP_CLAUSE_DECL (c) == decl)
12295 	      {
12296 		if (is_doacross && (collapse == 1 || i >= collapse))
12297 		  t = var;
12298 		else
12299 		  {
12300 		    t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
12301 		    gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
12302 		    gcc_assert (TREE_OPERAND (t, 0) == var);
12303 		    t = TREE_OPERAND (t, 1);
12304 		    gcc_assert (TREE_CODE (t) == PLUS_EXPR
12305 				|| TREE_CODE (t) == MINUS_EXPR
12306 				|| TREE_CODE (t) == POINTER_PLUS_EXPR);
12307 		    gcc_assert (TREE_OPERAND (t, 0) == var);
12308 		    t = build2 (TREE_CODE (t), TREE_TYPE (decl),
12309 				is_doacross ? var : decl,
12310 				TREE_OPERAND (t, 1));
12311 		  }
12312 		gimple_seq *seq;
12313 		if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE)
12314 		  seq = &OMP_CLAUSE_LASTPRIVATE_GIMPLE_SEQ (c);
12315 		else
12316 		  seq = &OMP_CLAUSE_LINEAR_GIMPLE_SEQ (c);
12317 		push_gimplify_context ();
12318 		gimplify_assign (decl, t, seq);
12319 		gimple *bind = NULL;
12320 		if (gimplify_ctxp->temps)
12321 		  {
12322 		    bind = gimple_build_bind (NULL_TREE, *seq, NULL_TREE);
12323 		    *seq = NULL;
12324 		    gimplify_seq_add_stmt (seq, bind);
12325 		  }
12326 		pop_gimplify_context (bind);
12327 	      }
12328 	}
12329       if (OMP_FOR_NON_RECTANGULAR (for_stmt) && var != decl)
12330 	for (int j = i + 1; j < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); j++)
12331 	  {
12332 	    t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), j);
12333 	    gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
12334 	    if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC
12335 		&& TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) == decl)
12336 	      TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) = var;
12337 	    t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), j);
12338 	    gcc_assert (COMPARISON_CLASS_P (t));
12339 	    if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC
12340 		&& TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) == decl)
12341 	      TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) = var;
12342 	  }
12343     }
12344 
12345   BITMAP_FREE (has_decl_expr);
12346   delete allocate_uids;
12347 
12348   if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP
12349       || (loop_p && orig_for_stmt == for_stmt))
12350     {
12351       push_gimplify_context ();
12352       if (TREE_CODE (OMP_FOR_BODY (orig_for_stmt)) != BIND_EXPR)
12353 	{
12354 	  OMP_FOR_BODY (orig_for_stmt)
12355 	    = build3 (BIND_EXPR, void_type_node, NULL,
12356 		      OMP_FOR_BODY (orig_for_stmt), NULL);
12357 	  TREE_SIDE_EFFECTS (OMP_FOR_BODY (orig_for_stmt)) = 1;
12358 	}
12359     }
12360 
12361   gimple *g = gimplify_and_return_first (OMP_FOR_BODY (orig_for_stmt),
12362 					 &for_body);
12363 
12364   if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP
12365       || (loop_p && orig_for_stmt == for_stmt))
12366     {
12367       if (gimple_code (g) == GIMPLE_BIND)
12368 	pop_gimplify_context (g);
12369       else
12370 	pop_gimplify_context (NULL);
12371     }
12372 
12373   if (orig_for_stmt != for_stmt)
12374     for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
12375       {
12376 	t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
12377 	decl = TREE_OPERAND (t, 0);
12378 	struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
12379 	if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
12380 	  gimplify_omp_ctxp = ctx->outer_context;
12381 	var = create_tmp_var (TREE_TYPE (decl), get_name (decl));
12382 	gimplify_omp_ctxp = ctx;
12383 	omp_add_variable (gimplify_omp_ctxp, var, GOVD_PRIVATE | GOVD_SEEN);
12384 	TREE_OPERAND (t, 0) = var;
12385 	t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
12386 	TREE_OPERAND (t, 1) = copy_node (TREE_OPERAND (t, 1));
12387 	TREE_OPERAND (TREE_OPERAND (t, 1), 0) = var;
12388 	if (OMP_FOR_NON_RECTANGULAR (for_stmt))
12389 	  for (int j = i + 1;
12390 	       j < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); j++)
12391 	    {
12392 	      t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), j);
12393 	      gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
12394 	      if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC
12395 		  && TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) == decl)
12396 		{
12397 		  TREE_OPERAND (t, 1) = copy_node (TREE_OPERAND (t, 1));
12398 		  TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) = var;
12399 		}
12400 	      t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), j);
12401 	      gcc_assert (COMPARISON_CLASS_P (t));
12402 	      if (TREE_CODE (TREE_OPERAND (t, 1)) == TREE_VEC
12403 		  && TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) == decl)
12404 		{
12405 		  TREE_OPERAND (t, 1) = copy_node (TREE_OPERAND (t, 1));
12406 		  TREE_VEC_ELT (TREE_OPERAND (t, 1), 0) = var;
12407 		}
12408 	  }
12409       }
12410 
12411   gimplify_adjust_omp_clauses (pre_p, for_body,
12412 			       &OMP_FOR_CLAUSES (orig_for_stmt),
12413 			       TREE_CODE (orig_for_stmt));
12414 
12415   int kind;
12416   switch (TREE_CODE (orig_for_stmt))
12417     {
12418     case OMP_FOR: kind = GF_OMP_FOR_KIND_FOR; break;
12419     case OMP_SIMD: kind = GF_OMP_FOR_KIND_SIMD; break;
12420     case OMP_DISTRIBUTE: kind = GF_OMP_FOR_KIND_DISTRIBUTE; break;
12421     case OMP_TASKLOOP: kind = GF_OMP_FOR_KIND_TASKLOOP; break;
12422     case OACC_LOOP: kind = GF_OMP_FOR_KIND_OACC_LOOP; break;
12423     default:
12424       gcc_unreachable ();
12425     }
12426   if (loop_p && kind == GF_OMP_FOR_KIND_SIMD)
12427     {
12428       gimplify_seq_add_seq (pre_p, for_pre_body);
12429       for_pre_body = NULL;
12430     }
12431   gfor = gimple_build_omp_for (for_body, kind, OMP_FOR_CLAUSES (orig_for_stmt),
12432 			       TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)),
12433 			       for_pre_body);
12434   if (orig_for_stmt != for_stmt)
12435     gimple_omp_for_set_combined_p (gfor, true);
12436   if (gimplify_omp_ctxp
12437       && (gimplify_omp_ctxp->combined_loop
12438 	  || (gimplify_omp_ctxp->region_type == ORT_COMBINED_PARALLEL
12439 	      && gimplify_omp_ctxp->outer_context
12440 	      && gimplify_omp_ctxp->outer_context->combined_loop)))
12441     {
12442       gimple_omp_for_set_combined_into_p (gfor, true);
12443       if (gimplify_omp_ctxp->combined_loop)
12444 	gcc_assert (TREE_CODE (orig_for_stmt) == OMP_SIMD);
12445       else
12446 	gcc_assert (TREE_CODE (orig_for_stmt) == OMP_FOR);
12447     }
12448 
12449   for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
12450     {
12451       t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
12452       gimple_omp_for_set_index (gfor, i, TREE_OPERAND (t, 0));
12453       gimple_omp_for_set_initial (gfor, i, TREE_OPERAND (t, 1));
12454       t = TREE_VEC_ELT (OMP_FOR_COND (for_stmt), i);
12455       gimple_omp_for_set_cond (gfor, i, TREE_CODE (t));
12456       gimple_omp_for_set_final (gfor, i, TREE_OPERAND (t, 1));
12457       t = TREE_VEC_ELT (OMP_FOR_INCR (for_stmt), i);
12458       gimple_omp_for_set_incr (gfor, i, TREE_OPERAND (t, 1));
12459     }
12460 
12461   /* OMP_TASKLOOP is gimplified as two GIMPLE_OMP_FOR taskloop
12462      constructs with GIMPLE_OMP_TASK sandwiched in between them.
12463      The outer taskloop stands for computing the number of iterations,
12464      counts for collapsed loops and holding taskloop specific clauses.
12465      The task construct stands for the effect of data sharing on the
12466      explicit task it creates and the inner taskloop stands for expansion
12467      of the static loop inside of the explicit task construct.  */
12468   if (TREE_CODE (orig_for_stmt) == OMP_TASKLOOP)
12469     {
12470       tree *gfor_clauses_ptr = gimple_omp_for_clauses_ptr (gfor);
12471       tree task_clauses = NULL_TREE;
12472       tree c = *gfor_clauses_ptr;
12473       tree *gtask_clauses_ptr = &task_clauses;
12474       tree outer_for_clauses = NULL_TREE;
12475       tree *gforo_clauses_ptr = &outer_for_clauses;
12476       bitmap lastprivate_uids = NULL;
12477       if (omp_find_clause (c, OMP_CLAUSE_ALLOCATE))
12478 	{
12479 	  c = omp_find_clause (c, OMP_CLAUSE_LASTPRIVATE);
12480 	  if (c)
12481 	    {
12482 	      lastprivate_uids = BITMAP_ALLOC (NULL);
12483 	      for (; c; c = omp_find_clause (OMP_CLAUSE_CHAIN (c),
12484 					     OMP_CLAUSE_LASTPRIVATE))
12485 		bitmap_set_bit (lastprivate_uids,
12486 				DECL_UID (OMP_CLAUSE_DECL (c)));
12487 	    }
12488 	  c = *gfor_clauses_ptr;
12489 	}
12490       for (; c; c = OMP_CLAUSE_CHAIN (c))
12491 	switch (OMP_CLAUSE_CODE (c))
12492 	  {
12493 	  /* These clauses are allowed on task, move them there.  */
12494 	  case OMP_CLAUSE_SHARED:
12495 	  case OMP_CLAUSE_FIRSTPRIVATE:
12496 	  case OMP_CLAUSE_DEFAULT:
12497 	  case OMP_CLAUSE_IF:
12498 	  case OMP_CLAUSE_UNTIED:
12499 	  case OMP_CLAUSE_FINAL:
12500 	  case OMP_CLAUSE_MERGEABLE:
12501 	  case OMP_CLAUSE_PRIORITY:
12502 	  case OMP_CLAUSE_REDUCTION:
12503 	  case OMP_CLAUSE_IN_REDUCTION:
12504 	    *gtask_clauses_ptr = c;
12505 	    gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12506 	    break;
12507 	  case OMP_CLAUSE_PRIVATE:
12508 	    if (OMP_CLAUSE_PRIVATE_TASKLOOP_IV (c))
12509 	      {
12510 		/* We want private on outer for and firstprivate
12511 		   on task.  */
12512 		*gtask_clauses_ptr
12513 		  = build_omp_clause (OMP_CLAUSE_LOCATION (c),
12514 				      OMP_CLAUSE_FIRSTPRIVATE);
12515 		OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
12516 		lang_hooks.decls.omp_finish_clause (*gtask_clauses_ptr, NULL,
12517 						    openacc);
12518 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
12519 		*gforo_clauses_ptr = c;
12520 		gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12521 	      }
12522 	    else
12523 	      {
12524 		*gtask_clauses_ptr = c;
12525 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12526 	      }
12527 	    break;
12528 	  /* These clauses go into outer taskloop clauses.  */
12529 	  case OMP_CLAUSE_GRAINSIZE:
12530 	  case OMP_CLAUSE_NUM_TASKS:
12531 	  case OMP_CLAUSE_NOGROUP:
12532 	    *gforo_clauses_ptr = c;
12533 	    gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12534 	    break;
12535 	  /* Collapse clause we duplicate on both taskloops.  */
12536 	  case OMP_CLAUSE_COLLAPSE:
12537 	    *gfor_clauses_ptr = c;
12538 	    gfor_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12539 	    *gforo_clauses_ptr = copy_node (c);
12540 	    gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (*gforo_clauses_ptr);
12541 	    break;
12542 	  /* For lastprivate, keep the clause on inner taskloop, and add
12543 	     a shared clause on task.  If the same decl is also firstprivate,
12544 	     add also firstprivate clause on the inner taskloop.  */
12545 	  case OMP_CLAUSE_LASTPRIVATE:
12546 	    if (OMP_CLAUSE_LASTPRIVATE_LOOP_IV (c))
12547 	      {
12548 		/* For taskloop C++ lastprivate IVs, we want:
12549 		   1) private on outer taskloop
12550 		   2) firstprivate and shared on task
12551 		   3) lastprivate on inner taskloop  */
12552 		*gtask_clauses_ptr
12553 		  = build_omp_clause (OMP_CLAUSE_LOCATION (c),
12554 				      OMP_CLAUSE_FIRSTPRIVATE);
12555 		OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
12556 		lang_hooks.decls.omp_finish_clause (*gtask_clauses_ptr, NULL,
12557 						    openacc);
12558 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
12559 		OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c) = 1;
12560 		*gforo_clauses_ptr = build_omp_clause (OMP_CLAUSE_LOCATION (c),
12561 						       OMP_CLAUSE_PRIVATE);
12562 		OMP_CLAUSE_DECL (*gforo_clauses_ptr) = OMP_CLAUSE_DECL (c);
12563 		OMP_CLAUSE_PRIVATE_TASKLOOP_IV (*gforo_clauses_ptr) = 1;
12564 		TREE_TYPE (*gforo_clauses_ptr) = TREE_TYPE (c);
12565 		gforo_clauses_ptr = &OMP_CLAUSE_CHAIN (*gforo_clauses_ptr);
12566 	      }
12567 	    *gfor_clauses_ptr = c;
12568 	    gfor_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12569 	    *gtask_clauses_ptr
12570 	      = build_omp_clause (OMP_CLAUSE_LOCATION (c), OMP_CLAUSE_SHARED);
12571 	    OMP_CLAUSE_DECL (*gtask_clauses_ptr) = OMP_CLAUSE_DECL (c);
12572 	    if (OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (c))
12573 	      OMP_CLAUSE_SHARED_FIRSTPRIVATE (*gtask_clauses_ptr) = 1;
12574 	    gtask_clauses_ptr
12575 	      = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
12576 	    break;
12577 	  /* Allocate clause we duplicate on task and inner taskloop
12578 	     if the decl is lastprivate, otherwise just put on task.  */
12579 	  case OMP_CLAUSE_ALLOCATE:
12580 	    if (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)
12581 		&& DECL_P (OMP_CLAUSE_ALLOCATE_ALLOCATOR (c)))
12582 	      {
12583 		/* Additionally, put firstprivate clause on task
12584 		   for the allocator if it is not constant.  */
12585 		*gtask_clauses_ptr
12586 		  = build_omp_clause (OMP_CLAUSE_LOCATION (c),
12587 				      OMP_CLAUSE_FIRSTPRIVATE);
12588 		OMP_CLAUSE_DECL (*gtask_clauses_ptr)
12589 		  = OMP_CLAUSE_ALLOCATE_ALLOCATOR (c);
12590 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
12591 	      }
12592 	    if (lastprivate_uids
12593 		&& bitmap_bit_p (lastprivate_uids,
12594 				 DECL_UID (OMP_CLAUSE_DECL (c))))
12595 	      {
12596 		*gfor_clauses_ptr = c;
12597 		gfor_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12598 		*gtask_clauses_ptr = copy_node (c);
12599 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (*gtask_clauses_ptr);
12600 	      }
12601 	    else
12602 	      {
12603 		*gtask_clauses_ptr = c;
12604 		gtask_clauses_ptr = &OMP_CLAUSE_CHAIN (c);
12605 	      }
12606 	    break;
12607 	  default:
12608 	    gcc_unreachable ();
12609 	  }
12610       *gfor_clauses_ptr = NULL_TREE;
12611       *gtask_clauses_ptr = NULL_TREE;
12612       *gforo_clauses_ptr = NULL_TREE;
12613       BITMAP_FREE (lastprivate_uids);
12614       g = gimple_build_bind (NULL_TREE, gfor, NULL_TREE);
12615       g = gimple_build_omp_task (g, task_clauses, NULL_TREE, NULL_TREE,
12616 				 NULL_TREE, NULL_TREE, NULL_TREE);
12617       gimple_omp_task_set_taskloop_p (g, true);
12618       g = gimple_build_bind (NULL_TREE, g, NULL_TREE);
12619       gomp_for *gforo
12620 	= gimple_build_omp_for (g, GF_OMP_FOR_KIND_TASKLOOP, outer_for_clauses,
12621 				gimple_omp_for_collapse (gfor),
12622 				gimple_omp_for_pre_body (gfor));
12623       gimple_omp_for_set_pre_body (gfor, NULL);
12624       gimple_omp_for_set_combined_p (gforo, true);
12625       gimple_omp_for_set_combined_into_p (gfor, true);
12626       for (i = 0; i < (int) gimple_omp_for_collapse (gfor); i++)
12627 	{
12628 	  tree type = TREE_TYPE (gimple_omp_for_index (gfor, i));
12629 	  tree v = create_tmp_var (type);
12630 	  gimple_omp_for_set_index (gforo, i, v);
12631 	  t = unshare_expr (gimple_omp_for_initial (gfor, i));
12632 	  gimple_omp_for_set_initial (gforo, i, t);
12633 	  gimple_omp_for_set_cond (gforo, i,
12634 				   gimple_omp_for_cond (gfor, i));
12635 	  t = unshare_expr (gimple_omp_for_final (gfor, i));
12636 	  gimple_omp_for_set_final (gforo, i, t);
12637 	  t = unshare_expr (gimple_omp_for_incr (gfor, i));
12638 	  gcc_assert (TREE_OPERAND (t, 0) == gimple_omp_for_index (gfor, i));
12639 	  TREE_OPERAND (t, 0) = v;
12640 	  gimple_omp_for_set_incr (gforo, i, t);
12641 	  t = build_omp_clause (input_location, OMP_CLAUSE_PRIVATE);
12642 	  OMP_CLAUSE_DECL (t) = v;
12643 	  OMP_CLAUSE_CHAIN (t) = gimple_omp_for_clauses (gforo);
12644 	  gimple_omp_for_set_clauses (gforo, t);
12645 	  if (OMP_FOR_NON_RECTANGULAR (for_stmt))
12646 	    {
12647 	      tree *p1 = NULL, *p2 = NULL;
12648 	      t = gimple_omp_for_initial (gforo, i);
12649 	      if (TREE_CODE (t) == TREE_VEC)
12650 		p1 = &TREE_VEC_ELT (t, 0);
12651 	      t = gimple_omp_for_final (gforo, i);
12652 	      if (TREE_CODE (t) == TREE_VEC)
12653 		{
12654 		  if (p1)
12655 		    p2 = &TREE_VEC_ELT (t, 0);
12656 		  else
12657 		    p1 = &TREE_VEC_ELT (t, 0);
12658 		}
12659 	      if (p1)
12660 		{
12661 		  int j;
12662 		  for (j = 0; j < i; j++)
12663 		    if (*p1 == gimple_omp_for_index (gfor, j))
12664 		      {
12665 			*p1 = gimple_omp_for_index (gforo, j);
12666 			if (p2)
12667 			  *p2 = *p1;
12668 			break;
12669 		      }
12670 		  gcc_assert (j < i);
12671 		}
12672 	    }
12673 	}
12674       gimplify_seq_add_stmt (pre_p, gforo);
12675     }
12676   else
12677     gimplify_seq_add_stmt (pre_p, gfor);
12678 
12679   if (TREE_CODE (orig_for_stmt) == OMP_FOR)
12680     {
12681       struct gimplify_omp_ctx *ctx = gimplify_omp_ctxp;
12682       unsigned lastprivate_conditional = 0;
12683       while (ctx
12684 	     && (ctx->region_type == ORT_TARGET_DATA
12685 		 || ctx->region_type == ORT_TASKGROUP))
12686 	ctx = ctx->outer_context;
12687       if (ctx && (ctx->region_type & ORT_PARALLEL) != 0)
12688 	for (tree c = gimple_omp_for_clauses (gfor);
12689 	     c; c = OMP_CLAUSE_CHAIN (c))
12690 	  if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
12691 	      && OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c))
12692 	    ++lastprivate_conditional;
12693       if (lastprivate_conditional)
12694 	{
12695 	  struct omp_for_data fd;
12696 	  omp_extract_for_data (gfor, &fd, NULL);
12697 	  tree type = build_array_type_nelts (unsigned_type_for (fd.iter_type),
12698 					      lastprivate_conditional);
12699 	  tree var = create_tmp_var_raw (type);
12700 	  tree c = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE__CONDTEMP_);
12701 	  OMP_CLAUSE_DECL (c) = var;
12702 	  OMP_CLAUSE_CHAIN (c) = gimple_omp_for_clauses (gfor);
12703 	  gimple_omp_for_set_clauses (gfor, c);
12704 	  omp_add_variable (ctx, var, GOVD_CONDTEMP | GOVD_SEEN);
12705 	}
12706     }
12707   else if (TREE_CODE (orig_for_stmt) == OMP_SIMD)
12708     {
12709       unsigned lastprivate_conditional = 0;
12710       for (tree c = gimple_omp_for_clauses (gfor); c; c = OMP_CLAUSE_CHAIN (c))
12711 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LASTPRIVATE
12712 	    && OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c))
12713 	  ++lastprivate_conditional;
12714       if (lastprivate_conditional)
12715 	{
12716 	  struct omp_for_data fd;
12717 	  omp_extract_for_data (gfor, &fd, NULL);
12718 	  tree type = unsigned_type_for (fd.iter_type);
12719 	  while (lastprivate_conditional--)
12720 	    {
12721 	      tree c = build_omp_clause (UNKNOWN_LOCATION,
12722 					 OMP_CLAUSE__CONDTEMP_);
12723 	      OMP_CLAUSE_DECL (c) = create_tmp_var (type);
12724 	      OMP_CLAUSE_CHAIN (c) = gimple_omp_for_clauses (gfor);
12725 	      gimple_omp_for_set_clauses (gfor, c);
12726 	    }
12727 	}
12728     }
12729 
12730   if (ret != GS_ALL_DONE)
12731     return GS_ERROR;
12732   *expr_p = NULL_TREE;
12733   return GS_ALL_DONE;
12734 }
12735 
12736 /* Helper for gimplify_omp_loop, called through walk_tree.  */
12737 
12738 static tree
replace_reduction_placeholders(tree * tp,int * walk_subtrees,void * data)12739 replace_reduction_placeholders (tree *tp, int *walk_subtrees, void *data)
12740 {
12741   if (DECL_P (*tp))
12742     {
12743       tree *d = (tree *) data;
12744       if (*tp == OMP_CLAUSE_REDUCTION_PLACEHOLDER (d[0]))
12745 	{
12746 	  *tp = OMP_CLAUSE_REDUCTION_PLACEHOLDER (d[1]);
12747 	  *walk_subtrees = 0;
12748 	}
12749       else if (*tp == OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (d[0]))
12750 	{
12751 	  *tp = OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (d[1]);
12752 	  *walk_subtrees = 0;
12753 	}
12754     }
12755   return NULL_TREE;
12756 }
12757 
12758 /* Gimplify the gross structure of an OMP_LOOP statement.  */
12759 
12760 static enum gimplify_status
gimplify_omp_loop(tree * expr_p,gimple_seq * pre_p)12761 gimplify_omp_loop (tree *expr_p, gimple_seq *pre_p)
12762 {
12763   tree for_stmt = *expr_p;
12764   tree clauses = OMP_FOR_CLAUSES (for_stmt);
12765   struct gimplify_omp_ctx *octx = gimplify_omp_ctxp;
12766   enum omp_clause_bind_kind kind = OMP_CLAUSE_BIND_THREAD;
12767   int i;
12768 
12769   /* If order is not present, the behavior is as if order(concurrent)
12770      appeared.  */
12771   tree order = omp_find_clause (clauses, OMP_CLAUSE_ORDER);
12772   if (order == NULL_TREE)
12773     {
12774       order = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_ORDER);
12775       OMP_CLAUSE_CHAIN (order) = clauses;
12776       OMP_FOR_CLAUSES (for_stmt) = clauses = order;
12777     }
12778 
12779   tree bind = omp_find_clause (clauses, OMP_CLAUSE_BIND);
12780   if (bind == NULL_TREE)
12781     {
12782       if (!flag_openmp) /* flag_openmp_simd */
12783 	;
12784       else if (octx && (octx->region_type & ORT_TEAMS) != 0)
12785 	kind = OMP_CLAUSE_BIND_TEAMS;
12786       else if (octx && (octx->region_type & ORT_PARALLEL) != 0)
12787 	kind = OMP_CLAUSE_BIND_PARALLEL;
12788       else
12789 	{
12790 	  for (; octx; octx = octx->outer_context)
12791 	    {
12792 	      if ((octx->region_type & ORT_ACC) != 0
12793 		  || octx->region_type == ORT_NONE
12794 		  || octx->region_type == ORT_IMPLICIT_TARGET)
12795 		continue;
12796 	      break;
12797 	    }
12798 	  if (octx == NULL && !in_omp_construct)
12799 	    error_at (EXPR_LOCATION (for_stmt),
12800 		      "%<bind%> clause not specified on a %<loop%> "
12801 		      "construct not nested inside another OpenMP construct");
12802 	}
12803       bind = build_omp_clause (UNKNOWN_LOCATION, OMP_CLAUSE_BIND);
12804       OMP_CLAUSE_CHAIN (bind) = clauses;
12805       OMP_CLAUSE_BIND_KIND (bind) = kind;
12806       OMP_FOR_CLAUSES (for_stmt) = bind;
12807     }
12808   else
12809     switch (OMP_CLAUSE_BIND_KIND (bind))
12810       {
12811       case OMP_CLAUSE_BIND_THREAD:
12812 	break;
12813       case OMP_CLAUSE_BIND_PARALLEL:
12814 	if (!flag_openmp) /* flag_openmp_simd */
12815 	  {
12816 	    OMP_CLAUSE_BIND_KIND (bind) = OMP_CLAUSE_BIND_THREAD;
12817 	    break;
12818 	  }
12819 	for (; octx; octx = octx->outer_context)
12820 	  if (octx->region_type == ORT_SIMD
12821 	      && omp_find_clause (octx->clauses, OMP_CLAUSE_BIND) == NULL_TREE)
12822 	    {
12823 	      error_at (EXPR_LOCATION (for_stmt),
12824 			"%<bind(parallel)%> on a %<loop%> construct nested "
12825 			"inside %<simd%> construct");
12826 	      OMP_CLAUSE_BIND_KIND (bind) = OMP_CLAUSE_BIND_THREAD;
12827 	      break;
12828 	    }
12829 	kind = OMP_CLAUSE_BIND_PARALLEL;
12830 	break;
12831       case OMP_CLAUSE_BIND_TEAMS:
12832 	if (!flag_openmp) /* flag_openmp_simd */
12833 	  {
12834 	    OMP_CLAUSE_BIND_KIND (bind) = OMP_CLAUSE_BIND_THREAD;
12835 	    break;
12836 	  }
12837 	if ((octx
12838 	     && octx->region_type != ORT_IMPLICIT_TARGET
12839 	     && octx->region_type != ORT_NONE
12840 	     && (octx->region_type & ORT_TEAMS) == 0)
12841 	    || in_omp_construct)
12842 	  {
12843 	    error_at (EXPR_LOCATION (for_stmt),
12844 		      "%<bind(teams)%> on a %<loop%> region not strictly "
12845 		      "nested inside of a %<teams%> region");
12846 	    OMP_CLAUSE_BIND_KIND (bind) = OMP_CLAUSE_BIND_THREAD;
12847 	    break;
12848 	  }
12849 	kind = OMP_CLAUSE_BIND_TEAMS;
12850 	break;
12851       default:
12852 	gcc_unreachable ();
12853       }
12854 
12855   for (tree *pc = &OMP_FOR_CLAUSES (for_stmt); *pc; )
12856     switch (OMP_CLAUSE_CODE (*pc))
12857       {
12858       case OMP_CLAUSE_REDUCTION:
12859 	if (OMP_CLAUSE_REDUCTION_INSCAN (*pc))
12860 	  {
12861 	    error_at (OMP_CLAUSE_LOCATION (*pc),
12862 		      "%<inscan%> %<reduction%> clause on "
12863 		      "%qs construct", "loop");
12864 	    OMP_CLAUSE_REDUCTION_INSCAN (*pc) = 0;
12865 	  }
12866 	if (OMP_CLAUSE_REDUCTION_TASK (*pc))
12867 	  {
12868 	    error_at (OMP_CLAUSE_LOCATION (*pc),
12869 		      "invalid %<task%> reduction modifier on construct "
12870 		      "other than %<parallel%>, %qs or %<sections%>",
12871 		      lang_GNU_Fortran () ? "do" : "for");
12872 	    OMP_CLAUSE_REDUCTION_TASK (*pc) = 0;
12873 	  }
12874 	pc = &OMP_CLAUSE_CHAIN (*pc);
12875 	break;
12876       case OMP_CLAUSE_LASTPRIVATE:
12877 	for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
12878 	  {
12879 	    tree t = TREE_VEC_ELT (OMP_FOR_INIT (for_stmt), i);
12880 	    gcc_assert (TREE_CODE (t) == MODIFY_EXPR);
12881 	    if (OMP_CLAUSE_DECL (*pc) == TREE_OPERAND (t, 0))
12882 	      break;
12883 	    if (OMP_FOR_ORIG_DECLS (for_stmt)
12884 		&& TREE_CODE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt),
12885 					    i)) == TREE_LIST
12886 		&& TREE_PURPOSE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt),
12887 					       i)))
12888 	      {
12889 		tree orig = TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i);
12890 		if (OMP_CLAUSE_DECL (*pc) == TREE_PURPOSE (orig))
12891 		  break;
12892 	      }
12893 	  }
12894 	if (i == TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)))
12895 	  {
12896 	    error_at (OMP_CLAUSE_LOCATION (*pc),
12897 		      "%<lastprivate%> clause on a %<loop%> construct refers "
12898 		      "to a variable %qD which is not the loop iterator",
12899 		      OMP_CLAUSE_DECL (*pc));
12900 	    *pc = OMP_CLAUSE_CHAIN (*pc);
12901 	    break;
12902 	  }
12903 	pc = &OMP_CLAUSE_CHAIN (*pc);
12904 	break;
12905       default:
12906 	pc = &OMP_CLAUSE_CHAIN (*pc);
12907 	break;
12908     }
12909 
12910   TREE_SET_CODE (for_stmt, OMP_SIMD);
12911 
12912   int last;
12913   switch (kind)
12914     {
12915     case OMP_CLAUSE_BIND_THREAD: last = 0; break;
12916     case OMP_CLAUSE_BIND_PARALLEL: last = 1; break;
12917     case OMP_CLAUSE_BIND_TEAMS: last = 2; break;
12918     }
12919   for (int pass = 1; pass <= last; pass++)
12920     {
12921       if (pass == 2)
12922 	{
12923 	  tree bind = build3 (BIND_EXPR, void_type_node, NULL, NULL, NULL);
12924 	  append_to_statement_list (*expr_p, &BIND_EXPR_BODY (bind));
12925 	  *expr_p = make_node (OMP_PARALLEL);
12926 	  TREE_TYPE (*expr_p) = void_type_node;
12927 	  OMP_PARALLEL_BODY (*expr_p) = bind;
12928 	  OMP_PARALLEL_COMBINED (*expr_p) = 1;
12929 	  SET_EXPR_LOCATION (*expr_p, EXPR_LOCATION (for_stmt));
12930 	  tree *pc = &OMP_PARALLEL_CLAUSES (*expr_p);
12931 	  for (i = 0; i < TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)); i++)
12932 	    if (OMP_FOR_ORIG_DECLS (for_stmt)
12933 		&& (TREE_CODE (TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i))
12934 		    == TREE_LIST))
12935 	      {
12936 		tree elt = TREE_VEC_ELT (OMP_FOR_ORIG_DECLS (for_stmt), i);
12937 		if (TREE_PURPOSE (elt) && TREE_VALUE (elt))
12938 		  {
12939 		    *pc = build_omp_clause (UNKNOWN_LOCATION,
12940 					    OMP_CLAUSE_FIRSTPRIVATE);
12941 		    OMP_CLAUSE_DECL (*pc) = TREE_VALUE (elt);
12942 		    pc = &OMP_CLAUSE_CHAIN (*pc);
12943 		  }
12944 	      }
12945 	}
12946       tree t = make_node (pass == 2 ? OMP_DISTRIBUTE : OMP_FOR);
12947       tree *pc = &OMP_FOR_CLAUSES (t);
12948       TREE_TYPE (t) = void_type_node;
12949       OMP_FOR_BODY (t) = *expr_p;
12950       SET_EXPR_LOCATION (t, EXPR_LOCATION (for_stmt));
12951       for (tree c = OMP_FOR_CLAUSES (for_stmt); c; c = OMP_CLAUSE_CHAIN (c))
12952 	switch (OMP_CLAUSE_CODE (c))
12953 	  {
12954 	  case OMP_CLAUSE_BIND:
12955 	  case OMP_CLAUSE_ORDER:
12956 	  case OMP_CLAUSE_COLLAPSE:
12957 	    *pc = copy_node (c);
12958 	    pc = &OMP_CLAUSE_CHAIN (*pc);
12959 	    break;
12960 	  case OMP_CLAUSE_PRIVATE:
12961 	  case OMP_CLAUSE_FIRSTPRIVATE:
12962 	    /* Only needed on innermost.  */
12963 	    break;
12964 	  case OMP_CLAUSE_LASTPRIVATE:
12965 	    if (OMP_CLAUSE_LASTPRIVATE_LOOP_IV (c) && pass != last)
12966 	      {
12967 		*pc = build_omp_clause (OMP_CLAUSE_LOCATION (c),
12968 					OMP_CLAUSE_FIRSTPRIVATE);
12969 		OMP_CLAUSE_DECL (*pc) = OMP_CLAUSE_DECL (c);
12970 		lang_hooks.decls.omp_finish_clause (*pc, NULL, false);
12971 		pc = &OMP_CLAUSE_CHAIN (*pc);
12972 	      }
12973 	    *pc = copy_node (c);
12974 	    OMP_CLAUSE_LASTPRIVATE_STMT (*pc) = NULL_TREE;
12975 	    TREE_TYPE (*pc) = unshare_expr (TREE_TYPE (c));
12976 	    if (OMP_CLAUSE_LASTPRIVATE_LOOP_IV (c))
12977 	      {
12978 		if (pass != last)
12979 		  OMP_CLAUSE_LASTPRIVATE_FIRSTPRIVATE (*pc) = 1;
12980 		else
12981 		  lang_hooks.decls.omp_finish_clause (*pc, NULL, false);
12982 		OMP_CLAUSE_LASTPRIVATE_LOOP_IV (*pc) = 0;
12983 	      }
12984 	    pc = &OMP_CLAUSE_CHAIN (*pc);
12985 	    break;
12986 	  case OMP_CLAUSE_REDUCTION:
12987 	    *pc = copy_node (c);
12988 	    OMP_CLAUSE_DECL (*pc) = unshare_expr (OMP_CLAUSE_DECL (c));
12989 	    TREE_TYPE (*pc) = unshare_expr (TREE_TYPE (c));
12990 	    OMP_CLAUSE_REDUCTION_INIT (*pc)
12991 	      = unshare_expr (OMP_CLAUSE_REDUCTION_INIT (c));
12992 	    OMP_CLAUSE_REDUCTION_MERGE (*pc)
12993 	      = unshare_expr (OMP_CLAUSE_REDUCTION_MERGE (c));
12994 	    if (OMP_CLAUSE_REDUCTION_PLACEHOLDER (*pc))
12995 	      {
12996 		OMP_CLAUSE_REDUCTION_PLACEHOLDER (*pc)
12997 		  = copy_node (OMP_CLAUSE_REDUCTION_PLACEHOLDER (c));
12998 		if (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (*pc))
12999 		  OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (*pc)
13000 		    = copy_node (OMP_CLAUSE_REDUCTION_DECL_PLACEHOLDER (c));
13001 		tree nc = *pc;
13002 		tree data[2] = { c, nc };
13003 		walk_tree_without_duplicates (&OMP_CLAUSE_REDUCTION_INIT (nc),
13004 					      replace_reduction_placeholders,
13005 					      data);
13006 		walk_tree_without_duplicates (&OMP_CLAUSE_REDUCTION_MERGE (nc),
13007 					      replace_reduction_placeholders,
13008 					      data);
13009 	      }
13010 	    pc = &OMP_CLAUSE_CHAIN (*pc);
13011 	    break;
13012 	  default:
13013 	    gcc_unreachable ();
13014 	  }
13015       *pc = NULL_TREE;
13016       *expr_p = t;
13017     }
13018   return gimplify_omp_for (expr_p, pre_p);
13019 }
13020 
13021 
13022 /* Helper function of optimize_target_teams, find OMP_TEAMS inside
13023    of OMP_TARGET's body.  */
13024 
13025 static tree
find_omp_teams(tree * tp,int * walk_subtrees,void *)13026 find_omp_teams (tree *tp, int *walk_subtrees, void *)
13027 {
13028   *walk_subtrees = 0;
13029   switch (TREE_CODE (*tp))
13030     {
13031     case OMP_TEAMS:
13032       return *tp;
13033     case BIND_EXPR:
13034     case STATEMENT_LIST:
13035       *walk_subtrees = 1;
13036       break;
13037     default:
13038       break;
13039     }
13040   return NULL_TREE;
13041 }
13042 
13043 /* Helper function of optimize_target_teams, determine if the expression
13044    can be computed safely before the target construct on the host.  */
13045 
13046 static tree
computable_teams_clause(tree * tp,int * walk_subtrees,void *)13047 computable_teams_clause (tree *tp, int *walk_subtrees, void *)
13048 {
13049   splay_tree_node n;
13050 
13051   if (TYPE_P (*tp))
13052     {
13053       *walk_subtrees = 0;
13054       return NULL_TREE;
13055     }
13056   switch (TREE_CODE (*tp))
13057     {
13058     case VAR_DECL:
13059     case PARM_DECL:
13060     case RESULT_DECL:
13061       *walk_subtrees = 0;
13062       if (error_operand_p (*tp)
13063 	  || !INTEGRAL_TYPE_P (TREE_TYPE (*tp))
13064 	  || DECL_HAS_VALUE_EXPR_P (*tp)
13065 	  || DECL_THREAD_LOCAL_P (*tp)
13066 	  || TREE_SIDE_EFFECTS (*tp)
13067 	  || TREE_THIS_VOLATILE (*tp))
13068 	return *tp;
13069       if (is_global_var (*tp)
13070 	  && (lookup_attribute ("omp declare target", DECL_ATTRIBUTES (*tp))
13071 	      || lookup_attribute ("omp declare target link",
13072 				   DECL_ATTRIBUTES (*tp))))
13073 	return *tp;
13074       if (VAR_P (*tp)
13075 	  && !DECL_SEEN_IN_BIND_EXPR_P (*tp)
13076 	  && !is_global_var (*tp)
13077 	  && decl_function_context (*tp) == current_function_decl)
13078 	return *tp;
13079       n = splay_tree_lookup (gimplify_omp_ctxp->variables,
13080 			     (splay_tree_key) *tp);
13081       if (n == NULL)
13082 	{
13083 	  if (gimplify_omp_ctxp->defaultmap[GDMK_SCALAR] & GOVD_FIRSTPRIVATE)
13084 	    return NULL_TREE;
13085 	  return *tp;
13086 	}
13087       else if (n->value & GOVD_LOCAL)
13088 	return *tp;
13089       else if (n->value & GOVD_FIRSTPRIVATE)
13090 	return NULL_TREE;
13091       else if ((n->value & (GOVD_MAP | GOVD_MAP_ALWAYS_TO))
13092 	       == (GOVD_MAP | GOVD_MAP_ALWAYS_TO))
13093 	return NULL_TREE;
13094       return *tp;
13095     case INTEGER_CST:
13096       if (!INTEGRAL_TYPE_P (TREE_TYPE (*tp)))
13097 	return *tp;
13098       return NULL_TREE;
13099     case TARGET_EXPR:
13100       if (TARGET_EXPR_INITIAL (*tp)
13101 	  || TREE_CODE (TARGET_EXPR_SLOT (*tp)) != VAR_DECL)
13102 	return *tp;
13103       return computable_teams_clause (&TARGET_EXPR_SLOT (*tp),
13104 				      walk_subtrees, NULL);
13105     /* Allow some reasonable subset of integral arithmetics.  */
13106     case PLUS_EXPR:
13107     case MINUS_EXPR:
13108     case MULT_EXPR:
13109     case TRUNC_DIV_EXPR:
13110     case CEIL_DIV_EXPR:
13111     case FLOOR_DIV_EXPR:
13112     case ROUND_DIV_EXPR:
13113     case TRUNC_MOD_EXPR:
13114     case CEIL_MOD_EXPR:
13115     case FLOOR_MOD_EXPR:
13116     case ROUND_MOD_EXPR:
13117     case RDIV_EXPR:
13118     case EXACT_DIV_EXPR:
13119     case MIN_EXPR:
13120     case MAX_EXPR:
13121     case LSHIFT_EXPR:
13122     case RSHIFT_EXPR:
13123     case BIT_IOR_EXPR:
13124     case BIT_XOR_EXPR:
13125     case BIT_AND_EXPR:
13126     case NEGATE_EXPR:
13127     case ABS_EXPR:
13128     case BIT_NOT_EXPR:
13129     case NON_LVALUE_EXPR:
13130     CASE_CONVERT:
13131       if (!INTEGRAL_TYPE_P (TREE_TYPE (*tp)))
13132 	return *tp;
13133       return NULL_TREE;
13134     /* And disallow anything else, except for comparisons.  */
13135     default:
13136       if (COMPARISON_CLASS_P (*tp))
13137 	return NULL_TREE;
13138       return *tp;
13139     }
13140 }
13141 
13142 /* Try to determine if the num_teams and/or thread_limit expressions
13143    can have their values determined already before entering the
13144    target construct.
13145    INTEGER_CSTs trivially are,
13146    integral decls that are firstprivate (explicitly or implicitly)
13147    or explicitly map(always, to:) or map(always, tofrom:) on the target
13148    region too, and expressions involving simple arithmetics on those
13149    too, function calls are not ok, dereferencing something neither etc.
13150    Add NUM_TEAMS and THREAD_LIMIT clauses to the OMP_CLAUSES of
13151    EXPR based on what we find:
13152    0 stands for clause not specified at all, use implementation default
13153    -1 stands for value that can't be determined easily before entering
13154       the target construct.
13155    If teams construct is not present at all, use 1 for num_teams
13156    and 0 for thread_limit (only one team is involved, and the thread
13157    limit is implementation defined.  */
13158 
13159 static void
optimize_target_teams(tree target,gimple_seq * pre_p)13160 optimize_target_teams (tree target, gimple_seq *pre_p)
13161 {
13162   tree body = OMP_BODY (target);
13163   tree teams = walk_tree (&body, find_omp_teams, NULL, NULL);
13164   tree num_teams = integer_zero_node;
13165   tree thread_limit = integer_zero_node;
13166   location_t num_teams_loc = EXPR_LOCATION (target);
13167   location_t thread_limit_loc = EXPR_LOCATION (target);
13168   tree c, *p, expr;
13169   struct gimplify_omp_ctx *target_ctx = gimplify_omp_ctxp;
13170 
13171   if (teams == NULL_TREE)
13172     num_teams = integer_one_node;
13173   else
13174     for (c = OMP_TEAMS_CLAUSES (teams); c; c = OMP_CLAUSE_CHAIN (c))
13175       {
13176 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_NUM_TEAMS)
13177 	  {
13178 	    p = &num_teams;
13179 	    num_teams_loc = OMP_CLAUSE_LOCATION (c);
13180 	  }
13181 	else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_THREAD_LIMIT)
13182 	  {
13183 	    p = &thread_limit;
13184 	    thread_limit_loc = OMP_CLAUSE_LOCATION (c);
13185 	  }
13186 	else
13187 	  continue;
13188 	expr = OMP_CLAUSE_OPERAND (c, 0);
13189 	if (TREE_CODE (expr) == INTEGER_CST)
13190 	  {
13191 	    *p = expr;
13192 	    continue;
13193 	  }
13194 	if (walk_tree (&expr, computable_teams_clause, NULL, NULL))
13195 	  {
13196 	    *p = integer_minus_one_node;
13197 	    continue;
13198 	  }
13199 	*p = expr;
13200 	gimplify_omp_ctxp = gimplify_omp_ctxp->outer_context;
13201 	if (gimplify_expr (p, pre_p, NULL, is_gimple_val, fb_rvalue, false)
13202 	    == GS_ERROR)
13203 	  {
13204 	    gimplify_omp_ctxp = target_ctx;
13205 	    *p = integer_minus_one_node;
13206 	    continue;
13207 	  }
13208 	gimplify_omp_ctxp = target_ctx;
13209 	if (!DECL_P (expr) && TREE_CODE (expr) != TARGET_EXPR)
13210 	  OMP_CLAUSE_OPERAND (c, 0) = *p;
13211       }
13212   c = build_omp_clause (thread_limit_loc, OMP_CLAUSE_THREAD_LIMIT);
13213   OMP_CLAUSE_THREAD_LIMIT_EXPR (c) = thread_limit;
13214   OMP_CLAUSE_CHAIN (c) = OMP_TARGET_CLAUSES (target);
13215   OMP_TARGET_CLAUSES (target) = c;
13216   c = build_omp_clause (num_teams_loc, OMP_CLAUSE_NUM_TEAMS);
13217   OMP_CLAUSE_NUM_TEAMS_EXPR (c) = num_teams;
13218   OMP_CLAUSE_CHAIN (c) = OMP_TARGET_CLAUSES (target);
13219   OMP_TARGET_CLAUSES (target) = c;
13220 }
13221 
13222 /* Gimplify the gross structure of several OMP constructs.  */
13223 
13224 static void
gimplify_omp_workshare(tree * expr_p,gimple_seq * pre_p)13225 gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
13226 {
13227   tree expr = *expr_p;
13228   gimple *stmt;
13229   gimple_seq body = NULL;
13230   enum omp_region_type ort;
13231 
13232   switch (TREE_CODE (expr))
13233     {
13234     case OMP_SECTIONS:
13235     case OMP_SINGLE:
13236       ort = ORT_WORKSHARE;
13237       break;
13238     case OMP_TARGET:
13239       ort = OMP_TARGET_COMBINED (expr) ? ORT_COMBINED_TARGET : ORT_TARGET;
13240       break;
13241     case OACC_KERNELS:
13242       ort = ORT_ACC_KERNELS;
13243       break;
13244     case OACC_PARALLEL:
13245       ort = ORT_ACC_PARALLEL;
13246       break;
13247     case OACC_SERIAL:
13248       ort = ORT_ACC_SERIAL;
13249       break;
13250     case OACC_DATA:
13251       ort = ORT_ACC_DATA;
13252       break;
13253     case OMP_TARGET_DATA:
13254       ort = ORT_TARGET_DATA;
13255       break;
13256     case OMP_TEAMS:
13257       ort = OMP_TEAMS_COMBINED (expr) ? ORT_COMBINED_TEAMS : ORT_TEAMS;
13258       if (gimplify_omp_ctxp == NULL
13259 	  || gimplify_omp_ctxp->region_type == ORT_IMPLICIT_TARGET)
13260 	ort = (enum omp_region_type) (ort | ORT_HOST_TEAMS);
13261       break;
13262     case OACC_HOST_DATA:
13263       ort = ORT_ACC_HOST_DATA;
13264       break;
13265     default:
13266       gcc_unreachable ();
13267     }
13268 
13269   bool save_in_omp_construct = in_omp_construct;
13270   if ((ort & ORT_ACC) == 0)
13271     in_omp_construct = false;
13272   gimplify_scan_omp_clauses (&OMP_CLAUSES (expr), pre_p, ort,
13273 			     TREE_CODE (expr));
13274   if (TREE_CODE (expr) == OMP_TARGET)
13275     optimize_target_teams (expr, pre_p);
13276   if ((ort & (ORT_TARGET | ORT_TARGET_DATA)) != 0
13277       || (ort & ORT_HOST_TEAMS) == ORT_HOST_TEAMS)
13278     {
13279       push_gimplify_context ();
13280       gimple *g = gimplify_and_return_first (OMP_BODY (expr), &body);
13281       if (gimple_code (g) == GIMPLE_BIND)
13282 	pop_gimplify_context (g);
13283       else
13284 	pop_gimplify_context (NULL);
13285       if ((ort & ORT_TARGET_DATA) != 0)
13286 	{
13287 	  enum built_in_function end_ix;
13288 	  switch (TREE_CODE (expr))
13289 	    {
13290 	    case OACC_DATA:
13291 	    case OACC_HOST_DATA:
13292 	      end_ix = BUILT_IN_GOACC_DATA_END;
13293 	      break;
13294 	    case OMP_TARGET_DATA:
13295 	      end_ix = BUILT_IN_GOMP_TARGET_END_DATA;
13296 	      break;
13297 	    default:
13298 	      gcc_unreachable ();
13299 	    }
13300 	  tree fn = builtin_decl_explicit (end_ix);
13301 	  g = gimple_build_call (fn, 0);
13302 	  gimple_seq cleanup = NULL;
13303 	  gimple_seq_add_stmt (&cleanup, g);
13304 	  g = gimple_build_try (body, cleanup, GIMPLE_TRY_FINALLY);
13305 	  body = NULL;
13306 	  gimple_seq_add_stmt (&body, g);
13307 	}
13308     }
13309   else
13310     gimplify_and_add (OMP_BODY (expr), &body);
13311   gimplify_adjust_omp_clauses (pre_p, body, &OMP_CLAUSES (expr),
13312 			       TREE_CODE (expr));
13313   in_omp_construct = save_in_omp_construct;
13314 
13315   switch (TREE_CODE (expr))
13316     {
13317     case OACC_DATA:
13318       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_DATA,
13319 				      OMP_CLAUSES (expr));
13320       break;
13321     case OACC_HOST_DATA:
13322       if (omp_find_clause (OMP_CLAUSES (expr), OMP_CLAUSE_IF_PRESENT))
13323 	{
13324 	  for (tree c = OMP_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
13325 	    if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR)
13326 	      OMP_CLAUSE_USE_DEVICE_PTR_IF_PRESENT (c) = 1;
13327 	}
13328 
13329       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_HOST_DATA,
13330 				      OMP_CLAUSES (expr));
13331       break;
13332     case OACC_KERNELS:
13333       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_KERNELS,
13334 				      OMP_CLAUSES (expr));
13335       break;
13336     case OACC_PARALLEL:
13337       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_PARALLEL,
13338 				      OMP_CLAUSES (expr));
13339       break;
13340     case OACC_SERIAL:
13341       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_SERIAL,
13342 				      OMP_CLAUSES (expr));
13343       break;
13344     case OMP_SECTIONS:
13345       stmt = gimple_build_omp_sections (body, OMP_CLAUSES (expr));
13346       break;
13347     case OMP_SINGLE:
13348       stmt = gimple_build_omp_single (body, OMP_CLAUSES (expr));
13349       break;
13350     case OMP_TARGET:
13351       stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_REGION,
13352 				      OMP_CLAUSES (expr));
13353       break;
13354     case OMP_TARGET_DATA:
13355       /* Put use_device_{ptr,addr} clauses last, as map clauses are supposed
13356 	 to be evaluated before the use_device_{ptr,addr} clauses if they
13357 	 refer to the same variables.  */
13358       {
13359 	tree use_device_clauses;
13360 	tree *pc, *uc = &use_device_clauses;
13361 	for (pc = &OMP_CLAUSES (expr); *pc; )
13362 	  if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_USE_DEVICE_PTR
13363 	      || OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_USE_DEVICE_ADDR)
13364 	    {
13365 	      *uc = *pc;
13366 	      *pc = OMP_CLAUSE_CHAIN (*pc);
13367 	      uc = &OMP_CLAUSE_CHAIN (*uc);
13368 	    }
13369 	  else
13370 	    pc = &OMP_CLAUSE_CHAIN (*pc);
13371 	*uc = NULL_TREE;
13372 	*pc = use_device_clauses;
13373 	stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_DATA,
13374 					OMP_CLAUSES (expr));
13375       }
13376       break;
13377     case OMP_TEAMS:
13378       stmt = gimple_build_omp_teams (body, OMP_CLAUSES (expr));
13379       if ((ort & ORT_HOST_TEAMS) == ORT_HOST_TEAMS)
13380 	gimple_omp_teams_set_host (as_a <gomp_teams *> (stmt), true);
13381       break;
13382     default:
13383       gcc_unreachable ();
13384     }
13385 
13386   gimplify_seq_add_stmt (pre_p, stmt);
13387   *expr_p = NULL_TREE;
13388 }
13389 
13390 /* Gimplify the gross structure of OpenACC enter/exit data, update, and OpenMP
13391    target update constructs.  */
13392 
13393 static void
gimplify_omp_target_update(tree * expr_p,gimple_seq * pre_p)13394 gimplify_omp_target_update (tree *expr_p, gimple_seq *pre_p)
13395 {
13396   tree expr = *expr_p;
13397   int kind;
13398   gomp_target *stmt;
13399   enum omp_region_type ort = ORT_WORKSHARE;
13400 
13401   switch (TREE_CODE (expr))
13402     {
13403     case OACC_ENTER_DATA:
13404     case OACC_EXIT_DATA:
13405       kind = GF_OMP_TARGET_KIND_OACC_ENTER_EXIT_DATA;
13406       ort = ORT_ACC;
13407       break;
13408     case OACC_UPDATE:
13409       kind = GF_OMP_TARGET_KIND_OACC_UPDATE;
13410       ort = ORT_ACC;
13411       break;
13412     case OMP_TARGET_UPDATE:
13413       kind = GF_OMP_TARGET_KIND_UPDATE;
13414       break;
13415     case OMP_TARGET_ENTER_DATA:
13416       kind = GF_OMP_TARGET_KIND_ENTER_DATA;
13417       break;
13418     case OMP_TARGET_EXIT_DATA:
13419       kind = GF_OMP_TARGET_KIND_EXIT_DATA;
13420       break;
13421     default:
13422       gcc_unreachable ();
13423     }
13424   gimplify_scan_omp_clauses (&OMP_STANDALONE_CLAUSES (expr), pre_p,
13425 			     ort, TREE_CODE (expr));
13426   gimplify_adjust_omp_clauses (pre_p, NULL, &OMP_STANDALONE_CLAUSES (expr),
13427 			       TREE_CODE (expr));
13428   if (TREE_CODE (expr) == OACC_UPDATE
13429       && omp_find_clause (OMP_STANDALONE_CLAUSES (expr),
13430 			  OMP_CLAUSE_IF_PRESENT))
13431     {
13432       /* The runtime uses GOMP_MAP_{TO,FROM} to denote the if_present
13433 	 clause.  */
13434       for (tree c = OMP_STANDALONE_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
13435 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP)
13436 	  switch (OMP_CLAUSE_MAP_KIND (c))
13437 	    {
13438 	    case GOMP_MAP_FORCE_TO:
13439 	      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_TO);
13440 	      break;
13441 	    case GOMP_MAP_FORCE_FROM:
13442 	      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_FROM);
13443 	      break;
13444 	    default:
13445 	      break;
13446 	    }
13447     }
13448   else if (TREE_CODE (expr) == OACC_EXIT_DATA
13449 	   && omp_find_clause (OMP_STANDALONE_CLAUSES (expr),
13450 			       OMP_CLAUSE_FINALIZE))
13451     {
13452       /* Use GOMP_MAP_DELETE/GOMP_MAP_FORCE_FROM to denote "finalize"
13453 	 semantics.  */
13454       bool have_clause = false;
13455       for (tree c = OMP_STANDALONE_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
13456 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_MAP)
13457 	  switch (OMP_CLAUSE_MAP_KIND (c))
13458 	    {
13459 	    case GOMP_MAP_FROM:
13460 	      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_FORCE_FROM);
13461 	      have_clause = true;
13462 	      break;
13463 	    case GOMP_MAP_RELEASE:
13464 	      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_DELETE);
13465 	      have_clause = true;
13466 	      break;
13467 	    case GOMP_MAP_TO_PSET:
13468 	      /* Fortran arrays with descriptors must map that descriptor when
13469 		 doing standalone "attach" operations (in OpenACC).  In that
13470 		 case GOMP_MAP_TO_PSET appears by itself with no preceding
13471 		 clause (see trans-openmp.c:gfc_trans_omp_clauses).  */
13472 	      break;
13473 	    case GOMP_MAP_POINTER:
13474 	      /* TODO PR92929: we may see these here, but they'll always follow
13475 		 one of the clauses above, and will be handled by libgomp as
13476 		 one group, so no handling required here.  */
13477 	      gcc_assert (have_clause);
13478 	      break;
13479 	    case GOMP_MAP_DETACH:
13480 	      OMP_CLAUSE_SET_MAP_KIND (c, GOMP_MAP_FORCE_DETACH);
13481 	      have_clause = false;
13482 	      break;
13483 	    case GOMP_MAP_STRUCT:
13484 	      have_clause = false;
13485 	      break;
13486 	    default:
13487 	      gcc_unreachable ();
13488 	    }
13489     }
13490   stmt = gimple_build_omp_target (NULL, kind, OMP_STANDALONE_CLAUSES (expr));
13491 
13492   gimplify_seq_add_stmt (pre_p, stmt);
13493   *expr_p = NULL_TREE;
13494 }
13495 
13496 /* A subroutine of gimplify_omp_atomic.  The front end is supposed to have
13497    stabilized the lhs of the atomic operation as *ADDR.  Return true if
13498    EXPR is this stabilized form.  */
13499 
13500 static bool
goa_lhs_expr_p(tree expr,tree addr)13501 goa_lhs_expr_p (tree expr, tree addr)
13502 {
13503   /* Also include casts to other type variants.  The C front end is fond
13504      of adding these for e.g. volatile variables.  This is like
13505      STRIP_TYPE_NOPS but includes the main variant lookup.  */
13506   STRIP_USELESS_TYPE_CONVERSION (expr);
13507 
13508   if (TREE_CODE (expr) == INDIRECT_REF)
13509     {
13510       expr = TREE_OPERAND (expr, 0);
13511       while (expr != addr
13512 	     && (CONVERT_EXPR_P (expr)
13513 		 || TREE_CODE (expr) == NON_LVALUE_EXPR)
13514 	     && TREE_CODE (expr) == TREE_CODE (addr)
13515 	     && types_compatible_p (TREE_TYPE (expr), TREE_TYPE (addr)))
13516 	{
13517 	  expr = TREE_OPERAND (expr, 0);
13518 	  addr = TREE_OPERAND (addr, 0);
13519 	}
13520       if (expr == addr)
13521 	return true;
13522       return (TREE_CODE (addr) == ADDR_EXPR
13523 	      && TREE_CODE (expr) == ADDR_EXPR
13524 	      && TREE_OPERAND (addr, 0) == TREE_OPERAND (expr, 0));
13525     }
13526   if (TREE_CODE (addr) == ADDR_EXPR && expr == TREE_OPERAND (addr, 0))
13527     return true;
13528   return false;
13529 }
13530 
13531 /* Walk *EXPR_P and replace appearances of *LHS_ADDR with LHS_VAR.  If an
13532    expression does not involve the lhs, evaluate it into a temporary.
13533    Return 1 if the lhs appeared as a subexpression, 0 if it did not,
13534    or -1 if an error was encountered.  */
13535 
13536 static int
goa_stabilize_expr(tree * expr_p,gimple_seq * pre_p,tree lhs_addr,tree lhs_var)13537 goa_stabilize_expr (tree *expr_p, gimple_seq *pre_p, tree lhs_addr,
13538 		    tree lhs_var)
13539 {
13540   tree expr = *expr_p;
13541   int saw_lhs;
13542 
13543   if (goa_lhs_expr_p (expr, lhs_addr))
13544     {
13545       *expr_p = lhs_var;
13546       return 1;
13547     }
13548   if (is_gimple_val (expr))
13549     return 0;
13550 
13551   saw_lhs = 0;
13552   switch (TREE_CODE_CLASS (TREE_CODE (expr)))
13553     {
13554     case tcc_binary:
13555     case tcc_comparison:
13556       saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 1), pre_p, lhs_addr,
13557 				     lhs_var);
13558       /* FALLTHRU */
13559     case tcc_unary:
13560       saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 0), pre_p, lhs_addr,
13561 				     lhs_var);
13562       break;
13563     case tcc_expression:
13564       switch (TREE_CODE (expr))
13565 	{
13566 	case TRUTH_ANDIF_EXPR:
13567 	case TRUTH_ORIF_EXPR:
13568 	case TRUTH_AND_EXPR:
13569 	case TRUTH_OR_EXPR:
13570 	case TRUTH_XOR_EXPR:
13571 	case BIT_INSERT_EXPR:
13572 	  saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 1), pre_p,
13573 					 lhs_addr, lhs_var);
13574 	  /* FALLTHRU */
13575 	case TRUTH_NOT_EXPR:
13576 	  saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 0), pre_p,
13577 					 lhs_addr, lhs_var);
13578 	  break;
13579 	case COMPOUND_EXPR:
13580 	  /* Break out any preevaluations from cp_build_modify_expr.  */
13581 	  for (; TREE_CODE (expr) == COMPOUND_EXPR;
13582 	       expr = TREE_OPERAND (expr, 1))
13583 	    gimplify_stmt (&TREE_OPERAND (expr, 0), pre_p);
13584 	  *expr_p = expr;
13585 	  return goa_stabilize_expr (expr_p, pre_p, lhs_addr, lhs_var);
13586 	default:
13587 	  break;
13588 	}
13589       break;
13590     case tcc_reference:
13591       if (TREE_CODE (expr) == BIT_FIELD_REF)
13592 	saw_lhs |= goa_stabilize_expr (&TREE_OPERAND (expr, 0), pre_p,
13593 				       lhs_addr, lhs_var);
13594       break;
13595     default:
13596       break;
13597     }
13598 
13599   if (saw_lhs == 0)
13600     {
13601       enum gimplify_status gs;
13602       gs = gimplify_expr (expr_p, pre_p, NULL, is_gimple_val, fb_rvalue);
13603       if (gs != GS_ALL_DONE)
13604 	saw_lhs = -1;
13605     }
13606 
13607   return saw_lhs;
13608 }
13609 
13610 /* Gimplify an OMP_ATOMIC statement.  */
13611 
13612 static enum gimplify_status
gimplify_omp_atomic(tree * expr_p,gimple_seq * pre_p)13613 gimplify_omp_atomic (tree *expr_p, gimple_seq *pre_p)
13614 {
13615   tree addr = TREE_OPERAND (*expr_p, 0);
13616   tree rhs = TREE_CODE (*expr_p) == OMP_ATOMIC_READ
13617 	     ? NULL : TREE_OPERAND (*expr_p, 1);
13618   tree type = TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (addr)));
13619   tree tmp_load;
13620   gomp_atomic_load *loadstmt;
13621   gomp_atomic_store *storestmt;
13622 
13623   tmp_load = create_tmp_reg (type);
13624   if (rhs && goa_stabilize_expr (&rhs, pre_p, addr, tmp_load) < 0)
13625     return GS_ERROR;
13626 
13627   if (gimplify_expr (&addr, pre_p, NULL, is_gimple_val, fb_rvalue)
13628       != GS_ALL_DONE)
13629     return GS_ERROR;
13630 
13631   loadstmt = gimple_build_omp_atomic_load (tmp_load, addr,
13632 					   OMP_ATOMIC_MEMORY_ORDER (*expr_p));
13633   gimplify_seq_add_stmt (pre_p, loadstmt);
13634   if (rhs)
13635     {
13636       /* BIT_INSERT_EXPR is not valid for non-integral bitfield
13637 	 representatives.  Use BIT_FIELD_REF on the lhs instead.  */
13638       if (TREE_CODE (rhs) == BIT_INSERT_EXPR
13639 	  && !INTEGRAL_TYPE_P (TREE_TYPE (tmp_load)))
13640 	{
13641 	  tree bitpos = TREE_OPERAND (rhs, 2);
13642 	  tree op1 = TREE_OPERAND (rhs, 1);
13643 	  tree bitsize;
13644 	  tree tmp_store = tmp_load;
13645 	  if (TREE_CODE (*expr_p) == OMP_ATOMIC_CAPTURE_OLD)
13646 	    tmp_store = get_initialized_tmp_var (tmp_load, pre_p);
13647 	  if (INTEGRAL_TYPE_P (TREE_TYPE (op1)))
13648 	    bitsize = bitsize_int (TYPE_PRECISION (TREE_TYPE (op1)));
13649 	  else
13650 	    bitsize = TYPE_SIZE (TREE_TYPE (op1));
13651 	  gcc_assert (TREE_OPERAND (rhs, 0) == tmp_load);
13652 	  tree t = build2_loc (EXPR_LOCATION (rhs),
13653 			       MODIFY_EXPR, void_type_node,
13654 			       build3_loc (EXPR_LOCATION (rhs), BIT_FIELD_REF,
13655 					   TREE_TYPE (op1), tmp_store, bitsize,
13656 					   bitpos), op1);
13657 	  gimplify_and_add (t, pre_p);
13658 	  rhs = tmp_store;
13659 	}
13660       if (gimplify_expr (&rhs, pre_p, NULL, is_gimple_val, fb_rvalue)
13661 	  != GS_ALL_DONE)
13662 	return GS_ERROR;
13663     }
13664 
13665   if (TREE_CODE (*expr_p) == OMP_ATOMIC_READ)
13666     rhs = tmp_load;
13667   storestmt
13668     = gimple_build_omp_atomic_store (rhs, OMP_ATOMIC_MEMORY_ORDER (*expr_p));
13669   gimplify_seq_add_stmt (pre_p, storestmt);
13670   switch (TREE_CODE (*expr_p))
13671     {
13672     case OMP_ATOMIC_READ:
13673     case OMP_ATOMIC_CAPTURE_OLD:
13674       *expr_p = tmp_load;
13675       gimple_omp_atomic_set_need_value (loadstmt);
13676       break;
13677     case OMP_ATOMIC_CAPTURE_NEW:
13678       *expr_p = rhs;
13679       gimple_omp_atomic_set_need_value (storestmt);
13680       break;
13681     default:
13682       *expr_p = NULL;
13683       break;
13684     }
13685 
13686   return GS_ALL_DONE;
13687 }
13688 
13689 /* Gimplify a TRANSACTION_EXPR.  This involves gimplification of the
13690    body, and adding some EH bits.  */
13691 
13692 static enum gimplify_status
gimplify_transaction(tree * expr_p,gimple_seq * pre_p)13693 gimplify_transaction (tree *expr_p, gimple_seq *pre_p)
13694 {
13695   tree expr = *expr_p, temp, tbody = TRANSACTION_EXPR_BODY (expr);
13696   gimple *body_stmt;
13697   gtransaction *trans_stmt;
13698   gimple_seq body = NULL;
13699   int subcode = 0;
13700 
13701   /* Wrap the transaction body in a BIND_EXPR so we have a context
13702      where to put decls for OMP.  */
13703   if (TREE_CODE (tbody) != BIND_EXPR)
13704     {
13705       tree bind = build3 (BIND_EXPR, void_type_node, NULL, tbody, NULL);
13706       TREE_SIDE_EFFECTS (bind) = 1;
13707       SET_EXPR_LOCATION (bind, EXPR_LOCATION (tbody));
13708       TRANSACTION_EXPR_BODY (expr) = bind;
13709     }
13710 
13711   push_gimplify_context ();
13712   temp = voidify_wrapper_expr (*expr_p, NULL);
13713 
13714   body_stmt = gimplify_and_return_first (TRANSACTION_EXPR_BODY (expr), &body);
13715   pop_gimplify_context (body_stmt);
13716 
13717   trans_stmt = gimple_build_transaction (body);
13718   if (TRANSACTION_EXPR_OUTER (expr))
13719     subcode = GTMA_IS_OUTER;
13720   else if (TRANSACTION_EXPR_RELAXED (expr))
13721     subcode = GTMA_IS_RELAXED;
13722   gimple_transaction_set_subcode (trans_stmt, subcode);
13723 
13724   gimplify_seq_add_stmt (pre_p, trans_stmt);
13725 
13726   if (temp)
13727     {
13728       *expr_p = temp;
13729       return GS_OK;
13730     }
13731 
13732   *expr_p = NULL_TREE;
13733   return GS_ALL_DONE;
13734 }
13735 
13736 /* Gimplify an OMP_ORDERED construct.  EXPR is the tree version.  BODY
13737    is the OMP_BODY of the original EXPR (which has already been
13738    gimplified so it's not present in the EXPR).
13739 
13740    Return the gimplified GIMPLE_OMP_ORDERED tuple.  */
13741 
13742 static gimple *
gimplify_omp_ordered(tree expr,gimple_seq body)13743 gimplify_omp_ordered (tree expr, gimple_seq body)
13744 {
13745   tree c, decls;
13746   int failures = 0;
13747   unsigned int i;
13748   tree source_c = NULL_TREE;
13749   tree sink_c = NULL_TREE;
13750 
13751   if (gimplify_omp_ctxp)
13752     {
13753       for (c = OMP_ORDERED_CLAUSES (expr); c; c = OMP_CLAUSE_CHAIN (c))
13754 	if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
13755 	    && gimplify_omp_ctxp->loop_iter_var.is_empty ()
13756 	    && (OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK
13757 		|| OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE))
13758 	  {
13759 	    error_at (OMP_CLAUSE_LOCATION (c),
13760 		      "%<ordered%> construct with %<depend%> clause must be "
13761 		      "closely nested inside a loop with %<ordered%> clause "
13762 		      "with a parameter");
13763 	    failures++;
13764 	  }
13765 	else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
13766 		 && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SINK)
13767 	  {
13768 	    bool fail = false;
13769 	    for (decls = OMP_CLAUSE_DECL (c), i = 0;
13770 		 decls && TREE_CODE (decls) == TREE_LIST;
13771 		 decls = TREE_CHAIN (decls), ++i)
13772 	      if (i >= gimplify_omp_ctxp->loop_iter_var.length () / 2)
13773 		continue;
13774 	      else if (TREE_VALUE (decls)
13775 		       != gimplify_omp_ctxp->loop_iter_var[2 * i])
13776 		{
13777 		  error_at (OMP_CLAUSE_LOCATION (c),
13778 			    "variable %qE is not an iteration "
13779 			    "of outermost loop %d, expected %qE",
13780 			    TREE_VALUE (decls), i + 1,
13781 			    gimplify_omp_ctxp->loop_iter_var[2 * i]);
13782 		  fail = true;
13783 		  failures++;
13784 		}
13785 	      else
13786 		TREE_VALUE (decls)
13787 		  = gimplify_omp_ctxp->loop_iter_var[2 * i + 1];
13788 	    if (!fail && i != gimplify_omp_ctxp->loop_iter_var.length () / 2)
13789 	      {
13790 		error_at (OMP_CLAUSE_LOCATION (c),
13791 			  "number of variables in %<depend%> clause with "
13792 			  "%<sink%> modifier does not match number of "
13793 			  "iteration variables");
13794 		failures++;
13795 	      }
13796 	    sink_c = c;
13797 	  }
13798 	else if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEPEND
13799 		 && OMP_CLAUSE_DEPEND_KIND (c) == OMP_CLAUSE_DEPEND_SOURCE)
13800 	  {
13801 	    if (source_c)
13802 	      {
13803 		error_at (OMP_CLAUSE_LOCATION (c),
13804 			  "more than one %<depend%> clause with %<source%> "
13805 			  "modifier on an %<ordered%> construct");
13806 		failures++;
13807 	      }
13808 	    else
13809 	      source_c = c;
13810 	  }
13811     }
13812   if (source_c && sink_c)
13813     {
13814       error_at (OMP_CLAUSE_LOCATION (source_c),
13815 		"%<depend%> clause with %<source%> modifier specified "
13816 		"together with %<depend%> clauses with %<sink%> modifier "
13817 		"on the same construct");
13818       failures++;
13819     }
13820 
13821   if (failures)
13822     return gimple_build_nop ();
13823   return gimple_build_omp_ordered (body, OMP_ORDERED_CLAUSES (expr));
13824 }
13825 
13826 /* Convert the GENERIC expression tree *EXPR_P to GIMPLE.  If the
13827    expression produces a value to be used as an operand inside a GIMPLE
13828    statement, the value will be stored back in *EXPR_P.  This value will
13829    be a tree of class tcc_declaration, tcc_constant, tcc_reference or
13830    an SSA_NAME.  The corresponding sequence of GIMPLE statements is
13831    emitted in PRE_P and POST_P.
13832 
13833    Additionally, this process may overwrite parts of the input
13834    expression during gimplification.  Ideally, it should be
13835    possible to do non-destructive gimplification.
13836 
13837    EXPR_P points to the GENERIC expression to convert to GIMPLE.  If
13838       the expression needs to evaluate to a value to be used as
13839       an operand in a GIMPLE statement, this value will be stored in
13840       *EXPR_P on exit.  This happens when the caller specifies one
13841       of fb_lvalue or fb_rvalue fallback flags.
13842 
13843    PRE_P will contain the sequence of GIMPLE statements corresponding
13844        to the evaluation of EXPR and all the side-effects that must
13845        be executed before the main expression.  On exit, the last
13846        statement of PRE_P is the core statement being gimplified.  For
13847        instance, when gimplifying 'if (++a)' the last statement in
13848        PRE_P will be 'if (t.1)' where t.1 is the result of
13849        pre-incrementing 'a'.
13850 
13851    POST_P will contain the sequence of GIMPLE statements corresponding
13852        to the evaluation of all the side-effects that must be executed
13853        after the main expression.  If this is NULL, the post
13854        side-effects are stored at the end of PRE_P.
13855 
13856        The reason why the output is split in two is to handle post
13857        side-effects explicitly.  In some cases, an expression may have
13858        inner and outer post side-effects which need to be emitted in
13859        an order different from the one given by the recursive
13860        traversal.  For instance, for the expression (*p--)++ the post
13861        side-effects of '--' must actually occur *after* the post
13862        side-effects of '++'.  However, gimplification will first visit
13863        the inner expression, so if a separate POST sequence was not
13864        used, the resulting sequence would be:
13865 
13866        	    1	t.1 = *p
13867        	    2	p = p - 1
13868        	    3	t.2 = t.1 + 1
13869        	    4	*p = t.2
13870 
13871        However, the post-decrement operation in line #2 must not be
13872        evaluated until after the store to *p at line #4, so the
13873        correct sequence should be:
13874 
13875        	    1	t.1 = *p
13876        	    2	t.2 = t.1 + 1
13877        	    3	*p = t.2
13878        	    4	p = p - 1
13879 
13880        So, by specifying a separate post queue, it is possible
13881        to emit the post side-effects in the correct order.
13882        If POST_P is NULL, an internal queue will be used.  Before
13883        returning to the caller, the sequence POST_P is appended to
13884        the main output sequence PRE_P.
13885 
13886    GIMPLE_TEST_F points to a function that takes a tree T and
13887        returns nonzero if T is in the GIMPLE form requested by the
13888        caller.  The GIMPLE predicates are in gimple.c.
13889 
13890    FALLBACK tells the function what sort of a temporary we want if
13891        gimplification cannot produce an expression that complies with
13892        GIMPLE_TEST_F.
13893 
13894        fb_none means that no temporary should be generated
13895        fb_rvalue means that an rvalue is OK to generate
13896        fb_lvalue means that an lvalue is OK to generate
13897        fb_either means that either is OK, but an lvalue is preferable.
13898        fb_mayfail means that gimplification may fail (in which case
13899        GS_ERROR will be returned)
13900 
13901    The return value is either GS_ERROR or GS_ALL_DONE, since this
13902    function iterates until EXPR is completely gimplified or an error
13903    occurs.  */
13904 
13905 enum gimplify_status
gimplify_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,bool (* gimple_test_f)(tree),fallback_t fallback)13906 gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
13907 	       bool (*gimple_test_f) (tree), fallback_t fallback)
13908 {
13909   tree tmp;
13910   gimple_seq internal_pre = NULL;
13911   gimple_seq internal_post = NULL;
13912   tree save_expr;
13913   bool is_statement;
13914   location_t saved_location;
13915   enum gimplify_status ret;
13916   gimple_stmt_iterator pre_last_gsi, post_last_gsi;
13917   tree label;
13918 
13919   save_expr = *expr_p;
13920   if (save_expr == NULL_TREE)
13921     return GS_ALL_DONE;
13922 
13923   /* If we are gimplifying a top-level statement, PRE_P must be valid.  */
13924   is_statement = gimple_test_f == is_gimple_stmt;
13925   if (is_statement)
13926     gcc_assert (pre_p);
13927 
13928   /* Consistency checks.  */
13929   if (gimple_test_f == is_gimple_reg)
13930     gcc_assert (fallback & (fb_rvalue | fb_lvalue));
13931   else if (gimple_test_f == is_gimple_val
13932            || gimple_test_f == is_gimple_call_addr
13933            || gimple_test_f == is_gimple_condexpr
13934 	   || gimple_test_f == is_gimple_condexpr_for_cond
13935            || gimple_test_f == is_gimple_mem_rhs
13936            || gimple_test_f == is_gimple_mem_rhs_or_call
13937            || gimple_test_f == is_gimple_reg_rhs
13938            || gimple_test_f == is_gimple_reg_rhs_or_call
13939            || gimple_test_f == is_gimple_asm_val
13940 	   || gimple_test_f == is_gimple_mem_ref_addr)
13941     gcc_assert (fallback & fb_rvalue);
13942   else if (gimple_test_f == is_gimple_min_lval
13943 	   || gimple_test_f == is_gimple_lvalue)
13944     gcc_assert (fallback & fb_lvalue);
13945   else if (gimple_test_f == is_gimple_addressable)
13946     gcc_assert (fallback & fb_either);
13947   else if (gimple_test_f == is_gimple_stmt)
13948     gcc_assert (fallback == fb_none);
13949   else
13950     {
13951       /* We should have recognized the GIMPLE_TEST_F predicate to
13952 	 know what kind of fallback to use in case a temporary is
13953 	 needed to hold the value or address of *EXPR_P.  */
13954       gcc_unreachable ();
13955     }
13956 
13957   /* We used to check the predicate here and return immediately if it
13958      succeeds.  This is wrong; the design is for gimplification to be
13959      idempotent, and for the predicates to only test for valid forms, not
13960      whether they are fully simplified.  */
13961   if (pre_p == NULL)
13962     pre_p = &internal_pre;
13963 
13964   if (post_p == NULL)
13965     post_p = &internal_post;
13966 
13967   /* Remember the last statements added to PRE_P and POST_P.  Every
13968      new statement added by the gimplification helpers needs to be
13969      annotated with location information.  To centralize the
13970      responsibility, we remember the last statement that had been
13971      added to both queues before gimplifying *EXPR_P.  If
13972      gimplification produces new statements in PRE_P and POST_P, those
13973      statements will be annotated with the same location information
13974      as *EXPR_P.  */
13975   pre_last_gsi = gsi_last (*pre_p);
13976   post_last_gsi = gsi_last (*post_p);
13977 
13978   saved_location = input_location;
13979   if (save_expr != error_mark_node
13980       && EXPR_HAS_LOCATION (*expr_p))
13981     input_location = EXPR_LOCATION (*expr_p);
13982 
13983   /* Loop over the specific gimplifiers until the toplevel node
13984      remains the same.  */
13985   do
13986     {
13987       /* Strip away as many useless type conversions as possible
13988 	 at the toplevel.  */
13989       STRIP_USELESS_TYPE_CONVERSION (*expr_p);
13990 
13991       /* Remember the expr.  */
13992       save_expr = *expr_p;
13993 
13994       /* Die, die, die, my darling.  */
13995       if (error_operand_p (save_expr))
13996 	{
13997 	  ret = GS_ERROR;
13998 	  break;
13999 	}
14000 
14001       /* Do any language-specific gimplification.  */
14002       ret = ((enum gimplify_status)
14003 	     lang_hooks.gimplify_expr (expr_p, pre_p, post_p));
14004       if (ret == GS_OK)
14005 	{
14006 	  if (*expr_p == NULL_TREE)
14007 	    break;
14008 	  if (*expr_p != save_expr)
14009 	    continue;
14010 	}
14011       else if (ret != GS_UNHANDLED)
14012 	break;
14013 
14014       /* Make sure that all the cases set 'ret' appropriately.  */
14015       ret = GS_UNHANDLED;
14016       switch (TREE_CODE (*expr_p))
14017 	{
14018 	  /* First deal with the special cases.  */
14019 
14020 	case POSTINCREMENT_EXPR:
14021 	case POSTDECREMENT_EXPR:
14022 	case PREINCREMENT_EXPR:
14023 	case PREDECREMENT_EXPR:
14024 	  ret = gimplify_self_mod_expr (expr_p, pre_p, post_p,
14025 					fallback != fb_none,
14026 					TREE_TYPE (*expr_p));
14027 	  break;
14028 
14029 	case VIEW_CONVERT_EXPR:
14030 	  if ((fallback & fb_rvalue)
14031 	      && is_gimple_reg_type (TREE_TYPE (*expr_p))
14032 	      && is_gimple_reg_type (TREE_TYPE (TREE_OPERAND (*expr_p, 0))))
14033 	    {
14034 	      ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14035 				   post_p, is_gimple_val, fb_rvalue);
14036 	      recalculate_side_effects (*expr_p);
14037 	      break;
14038 	    }
14039 	  /* Fallthru.  */
14040 
14041 	case ARRAY_REF:
14042 	case ARRAY_RANGE_REF:
14043 	case REALPART_EXPR:
14044 	case IMAGPART_EXPR:
14045 	case COMPONENT_REF:
14046 	  ret = gimplify_compound_lval (expr_p, pre_p, post_p,
14047 					fallback ? fallback : fb_rvalue);
14048 	  break;
14049 
14050 	case COND_EXPR:
14051 	  ret = gimplify_cond_expr (expr_p, pre_p, fallback);
14052 
14053 	  /* C99 code may assign to an array in a structure value of a
14054 	     conditional expression, and this has undefined behavior
14055 	     only on execution, so create a temporary if an lvalue is
14056 	     required.  */
14057 	  if (fallback == fb_lvalue)
14058 	    {
14059 	      *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
14060 	      mark_addressable (*expr_p);
14061 	      ret = GS_OK;
14062 	    }
14063 	  break;
14064 
14065 	case CALL_EXPR:
14066 	  ret = gimplify_call_expr (expr_p, pre_p, fallback != fb_none);
14067 
14068 	  /* C99 code may assign to an array in a structure returned
14069 	     from a function, and this has undefined behavior only on
14070 	     execution, so create a temporary if an lvalue is
14071 	     required.  */
14072 	  if (fallback == fb_lvalue)
14073 	    {
14074 	      *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
14075 	      mark_addressable (*expr_p);
14076 	      ret = GS_OK;
14077 	    }
14078 	  break;
14079 
14080 	case TREE_LIST:
14081 	  gcc_unreachable ();
14082 
14083 	case COMPOUND_EXPR:
14084 	  ret = gimplify_compound_expr (expr_p, pre_p, fallback != fb_none);
14085 	  break;
14086 
14087 	case COMPOUND_LITERAL_EXPR:
14088 	  ret = gimplify_compound_literal_expr (expr_p, pre_p,
14089 						gimple_test_f, fallback);
14090 	  break;
14091 
14092 	case MODIFY_EXPR:
14093 	case INIT_EXPR:
14094 	  ret = gimplify_modify_expr (expr_p, pre_p, post_p,
14095 				      fallback != fb_none);
14096 	  break;
14097 
14098 	case TRUTH_ANDIF_EXPR:
14099 	case TRUTH_ORIF_EXPR:
14100 	  {
14101 	    /* Preserve the original type of the expression and the
14102 	       source location of the outer expression.  */
14103 	    tree org_type = TREE_TYPE (*expr_p);
14104 	    *expr_p = gimple_boolify (*expr_p);
14105 	    *expr_p = build3_loc (input_location, COND_EXPR,
14106 				  org_type, *expr_p,
14107 				  fold_convert_loc
14108 				    (input_location,
14109 				     org_type, boolean_true_node),
14110 				  fold_convert_loc
14111 				    (input_location,
14112 				     org_type, boolean_false_node));
14113 	    ret = GS_OK;
14114 	    break;
14115 	  }
14116 
14117 	case TRUTH_NOT_EXPR:
14118 	  {
14119 	    tree type = TREE_TYPE (*expr_p);
14120 	    /* The parsers are careful to generate TRUTH_NOT_EXPR
14121 	       only with operands that are always zero or one.
14122 	       We do not fold here but handle the only interesting case
14123 	       manually, as fold may re-introduce the TRUTH_NOT_EXPR.  */
14124 	    *expr_p = gimple_boolify (*expr_p);
14125 	    if (TYPE_PRECISION (TREE_TYPE (*expr_p)) == 1)
14126 	      *expr_p = build1_loc (input_location, BIT_NOT_EXPR,
14127 				    TREE_TYPE (*expr_p),
14128 				    TREE_OPERAND (*expr_p, 0));
14129 	    else
14130 	      *expr_p = build2_loc (input_location, BIT_XOR_EXPR,
14131 				    TREE_TYPE (*expr_p),
14132 				    TREE_OPERAND (*expr_p, 0),
14133 				    build_int_cst (TREE_TYPE (*expr_p), 1));
14134 	    if (!useless_type_conversion_p (type, TREE_TYPE (*expr_p)))
14135 	      *expr_p = fold_convert_loc (input_location, type, *expr_p);
14136 	    ret = GS_OK;
14137 	    break;
14138 	  }
14139 
14140 	case ADDR_EXPR:
14141 	  ret = gimplify_addr_expr (expr_p, pre_p, post_p);
14142 	  break;
14143 
14144 	case ANNOTATE_EXPR:
14145 	  {
14146 	    tree cond = TREE_OPERAND (*expr_p, 0);
14147 	    tree kind = TREE_OPERAND (*expr_p, 1);
14148 	    tree data = TREE_OPERAND (*expr_p, 2);
14149 	    tree type = TREE_TYPE (cond);
14150 	    if (!INTEGRAL_TYPE_P (type))
14151 	      {
14152 		*expr_p = cond;
14153 		ret = GS_OK;
14154 		break;
14155 	      }
14156 	    tree tmp = create_tmp_var (type);
14157 	    gimplify_arg (&cond, pre_p, EXPR_LOCATION (*expr_p));
14158 	    gcall *call
14159 	      = gimple_build_call_internal (IFN_ANNOTATE, 3, cond, kind, data);
14160 	    gimple_call_set_lhs (call, tmp);
14161 	    gimplify_seq_add_stmt (pre_p, call);
14162 	    *expr_p = tmp;
14163 	    ret = GS_ALL_DONE;
14164 	    break;
14165 	  }
14166 
14167 	case VA_ARG_EXPR:
14168 	  ret = gimplify_va_arg_expr (expr_p, pre_p, post_p);
14169 	  break;
14170 
14171 	CASE_CONVERT:
14172 	  if (IS_EMPTY_STMT (*expr_p))
14173 	    {
14174 	      ret = GS_ALL_DONE;
14175 	      break;
14176 	    }
14177 
14178 	  if (VOID_TYPE_P (TREE_TYPE (*expr_p))
14179 	      || fallback == fb_none)
14180 	    {
14181 	      /* Just strip a conversion to void (or in void context) and
14182 		 try again.  */
14183 	      *expr_p = TREE_OPERAND (*expr_p, 0);
14184 	      ret = GS_OK;
14185 	      break;
14186 	    }
14187 
14188 	  ret = gimplify_conversion (expr_p);
14189 	  if (ret == GS_ERROR)
14190 	    break;
14191 	  if (*expr_p != save_expr)
14192 	    break;
14193 	  /* FALLTHRU */
14194 
14195 	case FIX_TRUNC_EXPR:
14196 	  /* unary_expr: ... | '(' cast ')' val | ...  */
14197 	  ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
14198 			       is_gimple_val, fb_rvalue);
14199 	  recalculate_side_effects (*expr_p);
14200 	  break;
14201 
14202 	case INDIRECT_REF:
14203 	  {
14204 	    bool volatilep = TREE_THIS_VOLATILE (*expr_p);
14205 	    bool notrap = TREE_THIS_NOTRAP (*expr_p);
14206 	    tree saved_ptr_type = TREE_TYPE (TREE_OPERAND (*expr_p, 0));
14207 
14208 	    *expr_p = fold_indirect_ref_loc (input_location, *expr_p);
14209 	    if (*expr_p != save_expr)
14210 	      {
14211 		ret = GS_OK;
14212 		break;
14213 	      }
14214 
14215 	    ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
14216 				 is_gimple_reg, fb_rvalue);
14217 	    if (ret == GS_ERROR)
14218 	      break;
14219 
14220 	    recalculate_side_effects (*expr_p);
14221 	    *expr_p = fold_build2_loc (input_location, MEM_REF,
14222 				       TREE_TYPE (*expr_p),
14223 				       TREE_OPERAND (*expr_p, 0),
14224 				       build_int_cst (saved_ptr_type, 0));
14225 	    TREE_THIS_VOLATILE (*expr_p) = volatilep;
14226 	    TREE_THIS_NOTRAP (*expr_p) = notrap;
14227 	    ret = GS_OK;
14228 	    break;
14229 	  }
14230 
14231 	/* We arrive here through the various re-gimplifcation paths.  */
14232 	case MEM_REF:
14233 	  /* First try re-folding the whole thing.  */
14234 	  tmp = fold_binary (MEM_REF, TREE_TYPE (*expr_p),
14235 			     TREE_OPERAND (*expr_p, 0),
14236 			     TREE_OPERAND (*expr_p, 1));
14237 	  if (tmp)
14238 	    {
14239 	      REF_REVERSE_STORAGE_ORDER (tmp)
14240 	        = REF_REVERSE_STORAGE_ORDER (*expr_p);
14241 	      *expr_p = tmp;
14242 	      recalculate_side_effects (*expr_p);
14243 	      ret = GS_OK;
14244 	      break;
14245 	    }
14246 	  /* Avoid re-gimplifying the address operand if it is already
14247 	     in suitable form.  Re-gimplifying would mark the address
14248 	     operand addressable.  Always gimplify when not in SSA form
14249 	     as we still may have to gimplify decls with value-exprs.  */
14250 	  if (!gimplify_ctxp || !gimple_in_ssa_p (cfun)
14251 	      || !is_gimple_mem_ref_addr (TREE_OPERAND (*expr_p, 0)))
14252 	    {
14253 	      ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
14254 				   is_gimple_mem_ref_addr, fb_rvalue);
14255 	      if (ret == GS_ERROR)
14256 		break;
14257 	    }
14258 	  recalculate_side_effects (*expr_p);
14259 	  ret = GS_ALL_DONE;
14260 	  break;
14261 
14262 	/* Constants need not be gimplified.  */
14263 	case INTEGER_CST:
14264 	case REAL_CST:
14265 	case FIXED_CST:
14266 	case STRING_CST:
14267 	case COMPLEX_CST:
14268 	case VECTOR_CST:
14269 	  /* Drop the overflow flag on constants, we do not want
14270 	     that in the GIMPLE IL.  */
14271 	  if (TREE_OVERFLOW_P (*expr_p))
14272 	    *expr_p = drop_tree_overflow (*expr_p);
14273 	  ret = GS_ALL_DONE;
14274 	  break;
14275 
14276 	case CONST_DECL:
14277 	  /* If we require an lvalue, such as for ADDR_EXPR, retain the
14278 	     CONST_DECL node.  Otherwise the decl is replaceable by its
14279 	     value.  */
14280 	  /* ??? Should be == fb_lvalue, but ADDR_EXPR passes fb_either.  */
14281 	  if (fallback & fb_lvalue)
14282 	    ret = GS_ALL_DONE;
14283 	  else
14284 	    {
14285 	      *expr_p = DECL_INITIAL (*expr_p);
14286 	      ret = GS_OK;
14287 	    }
14288 	  break;
14289 
14290 	case DECL_EXPR:
14291 	  ret = gimplify_decl_expr (expr_p, pre_p);
14292 	  break;
14293 
14294 	case BIND_EXPR:
14295 	  ret = gimplify_bind_expr (expr_p, pre_p);
14296 	  break;
14297 
14298 	case LOOP_EXPR:
14299 	  ret = gimplify_loop_expr (expr_p, pre_p);
14300 	  break;
14301 
14302 	case SWITCH_EXPR:
14303 	  ret = gimplify_switch_expr (expr_p, pre_p);
14304 	  break;
14305 
14306 	case EXIT_EXPR:
14307 	  ret = gimplify_exit_expr (expr_p);
14308 	  break;
14309 
14310 	case GOTO_EXPR:
14311 	  /* If the target is not LABEL, then it is a computed jump
14312 	     and the target needs to be gimplified.  */
14313 	  if (TREE_CODE (GOTO_DESTINATION (*expr_p)) != LABEL_DECL)
14314 	    {
14315 	      ret = gimplify_expr (&GOTO_DESTINATION (*expr_p), pre_p,
14316 				   NULL, is_gimple_val, fb_rvalue);
14317 	      if (ret == GS_ERROR)
14318 		break;
14319 	    }
14320 	  gimplify_seq_add_stmt (pre_p,
14321 			  gimple_build_goto (GOTO_DESTINATION (*expr_p)));
14322 	  ret = GS_ALL_DONE;
14323 	  break;
14324 
14325 	case PREDICT_EXPR:
14326 	  gimplify_seq_add_stmt (pre_p,
14327 			gimple_build_predict (PREDICT_EXPR_PREDICTOR (*expr_p),
14328 					      PREDICT_EXPR_OUTCOME (*expr_p)));
14329 	  ret = GS_ALL_DONE;
14330 	  break;
14331 
14332 	case LABEL_EXPR:
14333 	  ret = gimplify_label_expr (expr_p, pre_p);
14334 	  label = LABEL_EXPR_LABEL (*expr_p);
14335 	  gcc_assert (decl_function_context (label) == current_function_decl);
14336 
14337 	  /* If the label is used in a goto statement, or address of the label
14338 	     is taken, we need to unpoison all variables that were seen so far.
14339 	     Doing so would prevent us from reporting a false positives.  */
14340 	  if (asan_poisoned_variables
14341 	      && asan_used_labels != NULL
14342 	      && asan_used_labels->contains (label)
14343 	      && !gimplify_omp_ctxp)
14344 	    asan_poison_variables (asan_poisoned_variables, false, pre_p);
14345 	  break;
14346 
14347 	case CASE_LABEL_EXPR:
14348 	  ret = gimplify_case_label_expr (expr_p, pre_p);
14349 
14350 	  if (gimplify_ctxp->live_switch_vars)
14351 	    asan_poison_variables (gimplify_ctxp->live_switch_vars, false,
14352 				   pre_p);
14353 	  break;
14354 
14355 	case RETURN_EXPR:
14356 	  ret = gimplify_return_expr (*expr_p, pre_p);
14357 	  break;
14358 
14359 	case CONSTRUCTOR:
14360 	  /* Don't reduce this in place; let gimplify_init_constructor work its
14361 	     magic.  Buf if we're just elaborating this for side effects, just
14362 	     gimplify any element that has side-effects.  */
14363 	  if (fallback == fb_none)
14364 	    {
14365 	      unsigned HOST_WIDE_INT ix;
14366 	      tree val;
14367 	      tree temp = NULL_TREE;
14368 	      FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (*expr_p), ix, val)
14369 		if (TREE_SIDE_EFFECTS (val))
14370 		  append_to_statement_list (val, &temp);
14371 
14372 	      *expr_p = temp;
14373 	      ret = temp ? GS_OK : GS_ALL_DONE;
14374 	    }
14375 	  /* C99 code may assign to an array in a constructed
14376 	     structure or union, and this has undefined behavior only
14377 	     on execution, so create a temporary if an lvalue is
14378 	     required.  */
14379 	  else if (fallback == fb_lvalue)
14380 	    {
14381 	      *expr_p = get_initialized_tmp_var (*expr_p, pre_p, post_p, false);
14382 	      mark_addressable (*expr_p);
14383 	      ret = GS_OK;
14384 	    }
14385 	  else
14386 	    ret = GS_ALL_DONE;
14387 	  break;
14388 
14389 	  /* The following are special cases that are not handled by the
14390 	     original GIMPLE grammar.  */
14391 
14392 	  /* SAVE_EXPR nodes are converted into a GIMPLE identifier and
14393 	     eliminated.  */
14394 	case SAVE_EXPR:
14395 	  ret = gimplify_save_expr (expr_p, pre_p, post_p);
14396 	  break;
14397 
14398 	case BIT_FIELD_REF:
14399 	  ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14400 			       post_p, is_gimple_lvalue, fb_either);
14401 	  recalculate_side_effects (*expr_p);
14402 	  break;
14403 
14404 	case TARGET_MEM_REF:
14405 	  {
14406 	    enum gimplify_status r0 = GS_ALL_DONE, r1 = GS_ALL_DONE;
14407 
14408 	    if (TMR_BASE (*expr_p))
14409 	      r0 = gimplify_expr (&TMR_BASE (*expr_p), pre_p,
14410 				  post_p, is_gimple_mem_ref_addr, fb_either);
14411 	    if (TMR_INDEX (*expr_p))
14412 	      r1 = gimplify_expr (&TMR_INDEX (*expr_p), pre_p,
14413 				  post_p, is_gimple_val, fb_rvalue);
14414 	    if (TMR_INDEX2 (*expr_p))
14415 	      r1 = gimplify_expr (&TMR_INDEX2 (*expr_p), pre_p,
14416 				  post_p, is_gimple_val, fb_rvalue);
14417 	    /* TMR_STEP and TMR_OFFSET are always integer constants.  */
14418 	    ret = MIN (r0, r1);
14419 	  }
14420 	  break;
14421 
14422 	case NON_LVALUE_EXPR:
14423 	  /* This should have been stripped above.  */
14424 	  gcc_unreachable ();
14425 
14426 	case ASM_EXPR:
14427 	  ret = gimplify_asm_expr (expr_p, pre_p, post_p);
14428 	  break;
14429 
14430 	case TRY_FINALLY_EXPR:
14431 	case TRY_CATCH_EXPR:
14432 	  {
14433 	    gimple_seq eval, cleanup;
14434 	    gtry *try_;
14435 
14436 	    /* Calls to destructors are generated automatically in FINALLY/CATCH
14437 	       block. They should have location as UNKNOWN_LOCATION. However,
14438 	       gimplify_call_expr will reset these call stmts to input_location
14439 	       if it finds stmt's location is unknown. To prevent resetting for
14440 	       destructors, we set the input_location to unknown.
14441 	       Note that this only affects the destructor calls in FINALLY/CATCH
14442 	       block, and will automatically reset to its original value by the
14443 	       end of gimplify_expr.  */
14444 	    input_location = UNKNOWN_LOCATION;
14445 	    eval = cleanup = NULL;
14446 	    gimplify_and_add (TREE_OPERAND (*expr_p, 0), &eval);
14447 	    if (TREE_CODE (*expr_p) == TRY_FINALLY_EXPR
14448 		&& TREE_CODE (TREE_OPERAND (*expr_p, 1)) == EH_ELSE_EXPR)
14449 	      {
14450 		gimple_seq n = NULL, e = NULL;
14451 		gimplify_and_add (TREE_OPERAND (TREE_OPERAND (*expr_p, 1),
14452 						0), &n);
14453 		gimplify_and_add (TREE_OPERAND (TREE_OPERAND (*expr_p, 1),
14454 						1), &e);
14455 		if (!gimple_seq_empty_p (n) && !gimple_seq_empty_p (e))
14456 		  {
14457 		    geh_else *stmt = gimple_build_eh_else (n, e);
14458 		    gimple_seq_add_stmt (&cleanup, stmt);
14459 		  }
14460 	      }
14461 	    else
14462 	      gimplify_and_add (TREE_OPERAND (*expr_p, 1), &cleanup);
14463 	    /* Don't create bogus GIMPLE_TRY with empty cleanup.  */
14464 	    if (gimple_seq_empty_p (cleanup))
14465 	      {
14466 		gimple_seq_add_seq (pre_p, eval);
14467 		ret = GS_ALL_DONE;
14468 		break;
14469 	      }
14470 	    try_ = gimple_build_try (eval, cleanup,
14471 				     TREE_CODE (*expr_p) == TRY_FINALLY_EXPR
14472 				     ? GIMPLE_TRY_FINALLY
14473 				     : GIMPLE_TRY_CATCH);
14474 	    if (EXPR_HAS_LOCATION (save_expr))
14475 	      gimple_set_location (try_, EXPR_LOCATION (save_expr));
14476 	    else if (LOCATION_LOCUS (saved_location) != UNKNOWN_LOCATION)
14477 	      gimple_set_location (try_, saved_location);
14478 	    if (TREE_CODE (*expr_p) == TRY_CATCH_EXPR)
14479 	      gimple_try_set_catch_is_cleanup (try_,
14480 					       TRY_CATCH_IS_CLEANUP (*expr_p));
14481 	    gimplify_seq_add_stmt (pre_p, try_);
14482 	    ret = GS_ALL_DONE;
14483 	    break;
14484 	  }
14485 
14486 	case CLEANUP_POINT_EXPR:
14487 	  ret = gimplify_cleanup_point_expr (expr_p, pre_p);
14488 	  break;
14489 
14490 	case TARGET_EXPR:
14491 	  ret = gimplify_target_expr (expr_p, pre_p, post_p);
14492 	  break;
14493 
14494 	case CATCH_EXPR:
14495 	  {
14496 	    gimple *c;
14497 	    gimple_seq handler = NULL;
14498 	    gimplify_and_add (CATCH_BODY (*expr_p), &handler);
14499 	    c = gimple_build_catch (CATCH_TYPES (*expr_p), handler);
14500 	    gimplify_seq_add_stmt (pre_p, c);
14501 	    ret = GS_ALL_DONE;
14502 	    break;
14503 	  }
14504 
14505 	case EH_FILTER_EXPR:
14506 	  {
14507 	    gimple *ehf;
14508 	    gimple_seq failure = NULL;
14509 
14510 	    gimplify_and_add (EH_FILTER_FAILURE (*expr_p), &failure);
14511 	    ehf = gimple_build_eh_filter (EH_FILTER_TYPES (*expr_p), failure);
14512 	    gimple_set_no_warning (ehf, TREE_NO_WARNING (*expr_p));
14513 	    gimplify_seq_add_stmt (pre_p, ehf);
14514 	    ret = GS_ALL_DONE;
14515 	    break;
14516 	  }
14517 
14518 	case OBJ_TYPE_REF:
14519 	  {
14520 	    enum gimplify_status r0, r1;
14521 	    r0 = gimplify_expr (&OBJ_TYPE_REF_OBJECT (*expr_p), pre_p,
14522 				post_p, is_gimple_val, fb_rvalue);
14523 	    r1 = gimplify_expr (&OBJ_TYPE_REF_EXPR (*expr_p), pre_p,
14524 				post_p, is_gimple_val, fb_rvalue);
14525 	    TREE_SIDE_EFFECTS (*expr_p) = 0;
14526 	    ret = MIN (r0, r1);
14527 	  }
14528 	  break;
14529 
14530 	case LABEL_DECL:
14531 	  /* We get here when taking the address of a label.  We mark
14532 	     the label as "forced"; meaning it can never be removed and
14533 	     it is a potential target for any computed goto.  */
14534 	  FORCED_LABEL (*expr_p) = 1;
14535 	  ret = GS_ALL_DONE;
14536 	  break;
14537 
14538 	case STATEMENT_LIST:
14539 	  ret = gimplify_statement_list (expr_p, pre_p);
14540 	  break;
14541 
14542 	case WITH_SIZE_EXPR:
14543 	  {
14544 	    gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14545 			   post_p == &internal_post ? NULL : post_p,
14546 			   gimple_test_f, fallback);
14547 	    gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p, post_p,
14548 			   is_gimple_val, fb_rvalue);
14549 	    ret = GS_ALL_DONE;
14550 	  }
14551 	  break;
14552 
14553 	case VAR_DECL:
14554 	case PARM_DECL:
14555 	  ret = gimplify_var_or_parm_decl (expr_p);
14556 	  break;
14557 
14558 	case RESULT_DECL:
14559 	  /* When within an OMP context, notice uses of variables.  */
14560 	  if (gimplify_omp_ctxp)
14561 	    omp_notice_variable (gimplify_omp_ctxp, *expr_p, true);
14562 	  ret = GS_ALL_DONE;
14563 	  break;
14564 
14565 	case DEBUG_EXPR_DECL:
14566 	  gcc_unreachable ();
14567 
14568 	case DEBUG_BEGIN_STMT:
14569 	  gimplify_seq_add_stmt (pre_p,
14570 				 gimple_build_debug_begin_stmt
14571 				 (TREE_BLOCK (*expr_p),
14572 				  EXPR_LOCATION (*expr_p)));
14573 	  ret = GS_ALL_DONE;
14574 	  *expr_p = NULL;
14575 	  break;
14576 
14577 	case SSA_NAME:
14578 	  /* Allow callbacks into the gimplifier during optimization.  */
14579 	  ret = GS_ALL_DONE;
14580 	  break;
14581 
14582 	case OMP_PARALLEL:
14583 	  gimplify_omp_parallel (expr_p, pre_p);
14584 	  ret = GS_ALL_DONE;
14585 	  break;
14586 
14587 	case OMP_TASK:
14588 	  gimplify_omp_task (expr_p, pre_p);
14589 	  ret = GS_ALL_DONE;
14590 	  break;
14591 
14592 	case OMP_FOR:
14593 	case OMP_SIMD:
14594 	case OMP_DISTRIBUTE:
14595 	case OMP_TASKLOOP:
14596 	case OACC_LOOP:
14597 	  ret = gimplify_omp_for (expr_p, pre_p);
14598 	  break;
14599 
14600 	case OMP_LOOP:
14601 	  ret = gimplify_omp_loop (expr_p, pre_p);
14602 	  break;
14603 
14604 	case OACC_CACHE:
14605 	  gimplify_oacc_cache (expr_p, pre_p);
14606 	  ret = GS_ALL_DONE;
14607 	  break;
14608 
14609 	case OACC_DECLARE:
14610 	  gimplify_oacc_declare (expr_p, pre_p);
14611 	  ret = GS_ALL_DONE;
14612 	  break;
14613 
14614 	case OACC_HOST_DATA:
14615 	case OACC_DATA:
14616 	case OACC_KERNELS:
14617 	case OACC_PARALLEL:
14618 	case OACC_SERIAL:
14619 	case OMP_SECTIONS:
14620 	case OMP_SINGLE:
14621 	case OMP_TARGET:
14622 	case OMP_TARGET_DATA:
14623 	case OMP_TEAMS:
14624 	  gimplify_omp_workshare (expr_p, pre_p);
14625 	  ret = GS_ALL_DONE;
14626 	  break;
14627 
14628 	case OACC_ENTER_DATA:
14629 	case OACC_EXIT_DATA:
14630 	case OACC_UPDATE:
14631 	case OMP_TARGET_UPDATE:
14632 	case OMP_TARGET_ENTER_DATA:
14633 	case OMP_TARGET_EXIT_DATA:
14634 	  gimplify_omp_target_update (expr_p, pre_p);
14635 	  ret = GS_ALL_DONE;
14636 	  break;
14637 
14638 	case OMP_SECTION:
14639 	case OMP_MASTER:
14640 	case OMP_ORDERED:
14641 	case OMP_CRITICAL:
14642 	case OMP_SCAN:
14643 	  {
14644 	    gimple_seq body = NULL;
14645 	    gimple *g;
14646 	    bool saved_in_omp_construct = in_omp_construct;
14647 
14648 	    in_omp_construct = true;
14649 	    gimplify_and_add (OMP_BODY (*expr_p), &body);
14650 	    in_omp_construct = saved_in_omp_construct;
14651 	    switch (TREE_CODE (*expr_p))
14652 	      {
14653 	      case OMP_SECTION:
14654 	        g = gimple_build_omp_section (body);
14655 	        break;
14656 	      case OMP_MASTER:
14657 	        g = gimple_build_omp_master (body);
14658 		break;
14659 	      case OMP_ORDERED:
14660 		g = gimplify_omp_ordered (*expr_p, body);
14661 		break;
14662 	      case OMP_CRITICAL:
14663 		gimplify_scan_omp_clauses (&OMP_CRITICAL_CLAUSES (*expr_p),
14664 					   pre_p, ORT_WORKSHARE, OMP_CRITICAL);
14665 		gimplify_adjust_omp_clauses (pre_p, body,
14666 					     &OMP_CRITICAL_CLAUSES (*expr_p),
14667 					     OMP_CRITICAL);
14668 		g = gimple_build_omp_critical (body,
14669 		    			       OMP_CRITICAL_NAME (*expr_p),
14670 		    			       OMP_CRITICAL_CLAUSES (*expr_p));
14671 		break;
14672 	      case OMP_SCAN:
14673 		gimplify_scan_omp_clauses (&OMP_SCAN_CLAUSES (*expr_p),
14674 					   pre_p, ORT_WORKSHARE, OMP_SCAN);
14675 		gimplify_adjust_omp_clauses (pre_p, body,
14676 					     &OMP_SCAN_CLAUSES (*expr_p),
14677 					     OMP_SCAN);
14678 		g = gimple_build_omp_scan (body, OMP_SCAN_CLAUSES (*expr_p));
14679 		break;
14680 	      default:
14681 		gcc_unreachable ();
14682 	      }
14683 	    gimplify_seq_add_stmt (pre_p, g);
14684 	    ret = GS_ALL_DONE;
14685 	    break;
14686 	  }
14687 
14688 	case OMP_TASKGROUP:
14689 	  {
14690 	    gimple_seq body = NULL;
14691 
14692 	    tree *pclauses = &OMP_TASKGROUP_CLAUSES (*expr_p);
14693 	    bool saved_in_omp_construct = in_omp_construct;
14694 	    gimplify_scan_omp_clauses (pclauses, pre_p, ORT_TASKGROUP,
14695 				       OMP_TASKGROUP);
14696 	    gimplify_adjust_omp_clauses (pre_p, NULL, pclauses, OMP_TASKGROUP);
14697 
14698 	    in_omp_construct = true;
14699 	    gimplify_and_add (OMP_BODY (*expr_p), &body);
14700 	    in_omp_construct = saved_in_omp_construct;
14701 	    gimple_seq cleanup = NULL;
14702 	    tree fn = builtin_decl_explicit (BUILT_IN_GOMP_TASKGROUP_END);
14703 	    gimple *g = gimple_build_call (fn, 0);
14704 	    gimple_seq_add_stmt (&cleanup, g);
14705 	    g = gimple_build_try (body, cleanup, GIMPLE_TRY_FINALLY);
14706 	    body = NULL;
14707 	    gimple_seq_add_stmt (&body, g);
14708 	    g = gimple_build_omp_taskgroup (body, *pclauses);
14709 	    gimplify_seq_add_stmt (pre_p, g);
14710 	    ret = GS_ALL_DONE;
14711 	    break;
14712 	  }
14713 
14714 	case OMP_ATOMIC:
14715 	case OMP_ATOMIC_READ:
14716 	case OMP_ATOMIC_CAPTURE_OLD:
14717 	case OMP_ATOMIC_CAPTURE_NEW:
14718 	  ret = gimplify_omp_atomic (expr_p, pre_p);
14719 	  break;
14720 
14721 	case TRANSACTION_EXPR:
14722 	  ret = gimplify_transaction (expr_p, pre_p);
14723 	  break;
14724 
14725 	case TRUTH_AND_EXPR:
14726 	case TRUTH_OR_EXPR:
14727 	case TRUTH_XOR_EXPR:
14728 	  {
14729 	    tree orig_type = TREE_TYPE (*expr_p);
14730 	    tree new_type, xop0, xop1;
14731 	    *expr_p = gimple_boolify (*expr_p);
14732 	    new_type = TREE_TYPE (*expr_p);
14733 	    if (!useless_type_conversion_p (orig_type, new_type))
14734 	      {
14735 		*expr_p = fold_convert_loc (input_location, orig_type, *expr_p);
14736 		ret = GS_OK;
14737 		break;
14738 	      }
14739 
14740 	  /* Boolified binary truth expressions are semantically equivalent
14741 	     to bitwise binary expressions.  Canonicalize them to the
14742 	     bitwise variant.  */
14743 	    switch (TREE_CODE (*expr_p))
14744 	      {
14745 	      case TRUTH_AND_EXPR:
14746 		TREE_SET_CODE (*expr_p, BIT_AND_EXPR);
14747 		break;
14748 	      case TRUTH_OR_EXPR:
14749 		TREE_SET_CODE (*expr_p, BIT_IOR_EXPR);
14750 		break;
14751 	      case TRUTH_XOR_EXPR:
14752 		TREE_SET_CODE (*expr_p, BIT_XOR_EXPR);
14753 		break;
14754 	      default:
14755 		break;
14756 	      }
14757 	    /* Now make sure that operands have compatible type to
14758 	       expression's new_type.  */
14759 	    xop0 = TREE_OPERAND (*expr_p, 0);
14760 	    xop1 = TREE_OPERAND (*expr_p, 1);
14761 	    if (!useless_type_conversion_p (new_type, TREE_TYPE (xop0)))
14762 	      TREE_OPERAND (*expr_p, 0) = fold_convert_loc (input_location,
14763 							    new_type,
14764 	      						    xop0);
14765 	    if (!useless_type_conversion_p (new_type, TREE_TYPE (xop1)))
14766 	      TREE_OPERAND (*expr_p, 1) = fold_convert_loc (input_location,
14767 							    new_type,
14768 	      						    xop1);
14769 	    /* Continue classified as tcc_binary.  */
14770 	    goto expr_2;
14771 	  }
14772 
14773 	case VEC_COND_EXPR:
14774 	  goto expr_3;
14775 
14776 	case VEC_PERM_EXPR:
14777 	  /* Classified as tcc_expression.  */
14778 	  goto expr_3;
14779 
14780 	case BIT_INSERT_EXPR:
14781 	  /* Argument 3 is a constant.  */
14782 	  goto expr_2;
14783 
14784 	case POINTER_PLUS_EXPR:
14785 	  {
14786 	    enum gimplify_status r0, r1;
14787 	    r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14788 				post_p, is_gimple_val, fb_rvalue);
14789 	    r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
14790 				post_p, is_gimple_val, fb_rvalue);
14791 	    recalculate_side_effects (*expr_p);
14792 	    ret = MIN (r0, r1);
14793 	    break;
14794 	  }
14795 
14796 	default:
14797 	  switch (TREE_CODE_CLASS (TREE_CODE (*expr_p)))
14798 	    {
14799 	    case tcc_comparison:
14800 	      /* Handle comparison of objects of non scalar mode aggregates
14801 	     	 with a call to memcmp.  It would be nice to only have to do
14802 	     	 this for variable-sized objects, but then we'd have to allow
14803 	     	 the same nest of reference nodes we allow for MODIFY_EXPR and
14804 	     	 that's too complex.
14805 
14806 		 Compare scalar mode aggregates as scalar mode values.  Using
14807 		 memcmp for them would be very inefficient at best, and is
14808 		 plain wrong if bitfields are involved.  */
14809 		{
14810 		  tree type = TREE_TYPE (TREE_OPERAND (*expr_p, 1));
14811 
14812 		  /* Vector comparisons need no boolification.  */
14813 		  if (TREE_CODE (type) == VECTOR_TYPE)
14814 		    goto expr_2;
14815 		  else if (!AGGREGATE_TYPE_P (type))
14816 		    {
14817 		      tree org_type = TREE_TYPE (*expr_p);
14818 		      *expr_p = gimple_boolify (*expr_p);
14819 		      if (!useless_type_conversion_p (org_type,
14820 						      TREE_TYPE (*expr_p)))
14821 			{
14822 			  *expr_p = fold_convert_loc (input_location,
14823 						      org_type, *expr_p);
14824 			  ret = GS_OK;
14825 			}
14826 		      else
14827 			goto expr_2;
14828 		    }
14829 		  else if (TYPE_MODE (type) != BLKmode)
14830 		    ret = gimplify_scalar_mode_aggregate_compare (expr_p);
14831 		  else
14832 		    ret = gimplify_variable_sized_compare (expr_p);
14833 
14834 		  break;
14835 		}
14836 
14837 	    /* If *EXPR_P does not need to be special-cased, handle it
14838 	       according to its class.  */
14839 	    case tcc_unary:
14840 	      ret = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14841 				   post_p, is_gimple_val, fb_rvalue);
14842 	      break;
14843 
14844 	    case tcc_binary:
14845 	    expr_2:
14846 	      {
14847 		enum gimplify_status r0, r1;
14848 
14849 		r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14850 		                    post_p, is_gimple_val, fb_rvalue);
14851 		r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
14852 				    post_p, is_gimple_val, fb_rvalue);
14853 
14854 		ret = MIN (r0, r1);
14855 		break;
14856 	      }
14857 
14858 	    expr_3:
14859 	      {
14860 		enum gimplify_status r0, r1, r2;
14861 
14862 		r0 = gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p,
14863 		                    post_p, is_gimple_val, fb_rvalue);
14864 		r1 = gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p,
14865 				    post_p, is_gimple_val, fb_rvalue);
14866 		r2 = gimplify_expr (&TREE_OPERAND (*expr_p, 2), pre_p,
14867 				    post_p, is_gimple_val, fb_rvalue);
14868 
14869 		ret = MIN (MIN (r0, r1), r2);
14870 		break;
14871 	      }
14872 
14873 	    case tcc_declaration:
14874 	    case tcc_constant:
14875 	      ret = GS_ALL_DONE;
14876 	      goto dont_recalculate;
14877 
14878 	    default:
14879 	      gcc_unreachable ();
14880 	    }
14881 
14882 	  recalculate_side_effects (*expr_p);
14883 
14884 	dont_recalculate:
14885 	  break;
14886 	}
14887 
14888       gcc_assert (*expr_p || ret != GS_OK);
14889     }
14890   while (ret == GS_OK);
14891 
14892   /* If we encountered an error_mark somewhere nested inside, either
14893      stub out the statement or propagate the error back out.  */
14894   if (ret == GS_ERROR)
14895     {
14896       if (is_statement)
14897 	*expr_p = NULL;
14898       goto out;
14899     }
14900 
14901   /* This was only valid as a return value from the langhook, which
14902      we handled.  Make sure it doesn't escape from any other context.  */
14903   gcc_assert (ret != GS_UNHANDLED);
14904 
14905   if (fallback == fb_none && *expr_p && !is_gimple_stmt (*expr_p))
14906     {
14907       /* We aren't looking for a value, and we don't have a valid
14908 	 statement.  If it doesn't have side-effects, throw it away.
14909 	 We can also get here with code such as "*&&L;", where L is
14910 	 a LABEL_DECL that is marked as FORCED_LABEL.  */
14911       if (TREE_CODE (*expr_p) == LABEL_DECL
14912 	  || !TREE_SIDE_EFFECTS (*expr_p))
14913 	*expr_p = NULL;
14914       else if (!TREE_THIS_VOLATILE (*expr_p))
14915 	{
14916 	  /* This is probably a _REF that contains something nested that
14917 	     has side effects.  Recurse through the operands to find it.  */
14918 	  enum tree_code code = TREE_CODE (*expr_p);
14919 
14920 	  switch (code)
14921 	    {
14922 	    case COMPONENT_REF:
14923 	    case REALPART_EXPR:
14924 	    case IMAGPART_EXPR:
14925 	    case VIEW_CONVERT_EXPR:
14926 	      gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
14927 			     gimple_test_f, fallback);
14928 	      break;
14929 
14930 	    case ARRAY_REF:
14931 	    case ARRAY_RANGE_REF:
14932 	      gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
14933 			     gimple_test_f, fallback);
14934 	      gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p, post_p,
14935 			     gimple_test_f, fallback);
14936 	      break;
14937 
14938 	    default:
14939 	       /* Anything else with side-effects must be converted to
14940 		  a valid statement before we get here.  */
14941 	      gcc_unreachable ();
14942 	    }
14943 
14944 	  *expr_p = NULL;
14945 	}
14946       else if (COMPLETE_TYPE_P (TREE_TYPE (*expr_p))
14947 	       && TYPE_MODE (TREE_TYPE (*expr_p)) != BLKmode)
14948 	{
14949 	  /* Historically, the compiler has treated a bare reference
14950 	     to a non-BLKmode volatile lvalue as forcing a load.  */
14951 	  tree type = TYPE_MAIN_VARIANT (TREE_TYPE (*expr_p));
14952 
14953 	  /* Normally, we do not want to create a temporary for a
14954 	     TREE_ADDRESSABLE type because such a type should not be
14955 	     copied by bitwise-assignment.  However, we make an
14956 	     exception here, as all we are doing here is ensuring that
14957 	     we read the bytes that make up the type.  We use
14958 	     create_tmp_var_raw because create_tmp_var will abort when
14959 	     given a TREE_ADDRESSABLE type.  */
14960 	  tree tmp = create_tmp_var_raw (type, "vol");
14961 	  gimple_add_tmp_var (tmp);
14962 	  gimplify_assign (tmp, *expr_p, pre_p);
14963 	  *expr_p = NULL;
14964 	}
14965       else
14966 	/* We can't do anything useful with a volatile reference to
14967 	   an incomplete type, so just throw it away.  Likewise for
14968 	   a BLKmode type, since any implicit inner load should
14969 	   already have been turned into an explicit one by the
14970 	   gimplification process.  */
14971 	*expr_p = NULL;
14972     }
14973 
14974   /* If we are gimplifying at the statement level, we're done.  Tack
14975      everything together and return.  */
14976   if (fallback == fb_none || is_statement)
14977     {
14978       /* Since *EXPR_P has been converted into a GIMPLE tuple, clear
14979          it out for GC to reclaim it.  */
14980       *expr_p = NULL_TREE;
14981 
14982       if (!gimple_seq_empty_p (internal_pre)
14983 	  || !gimple_seq_empty_p (internal_post))
14984 	{
14985 	  gimplify_seq_add_seq (&internal_pre, internal_post);
14986 	  gimplify_seq_add_seq (pre_p, internal_pre);
14987 	}
14988 
14989       /* The result of gimplifying *EXPR_P is going to be the last few
14990 	 statements in *PRE_P and *POST_P.  Add location information
14991 	 to all the statements that were added by the gimplification
14992 	 helpers.  */
14993       if (!gimple_seq_empty_p (*pre_p))
14994 	annotate_all_with_location_after (*pre_p, pre_last_gsi, input_location);
14995 
14996       if (!gimple_seq_empty_p (*post_p))
14997 	annotate_all_with_location_after (*post_p, post_last_gsi,
14998 					  input_location);
14999 
15000       goto out;
15001     }
15002 
15003 #ifdef ENABLE_GIMPLE_CHECKING
15004   if (*expr_p)
15005     {
15006       enum tree_code code = TREE_CODE (*expr_p);
15007       /* These expressions should already be in gimple IR form.  */
15008       gcc_assert (code != MODIFY_EXPR
15009 		  && code != ASM_EXPR
15010 		  && code != BIND_EXPR
15011 		  && code != CATCH_EXPR
15012 		  && (code != COND_EXPR || gimplify_ctxp->allow_rhs_cond_expr)
15013 		  && code != EH_FILTER_EXPR
15014 		  && code != GOTO_EXPR
15015 		  && code != LABEL_EXPR
15016 		  && code != LOOP_EXPR
15017 		  && code != SWITCH_EXPR
15018 		  && code != TRY_FINALLY_EXPR
15019 		  && code != EH_ELSE_EXPR
15020 		  && code != OACC_PARALLEL
15021 		  && code != OACC_KERNELS
15022 		  && code != OACC_SERIAL
15023 		  && code != OACC_DATA
15024 		  && code != OACC_HOST_DATA
15025 		  && code != OACC_DECLARE
15026 		  && code != OACC_UPDATE
15027 		  && code != OACC_ENTER_DATA
15028 		  && code != OACC_EXIT_DATA
15029 		  && code != OACC_CACHE
15030 		  && code != OMP_CRITICAL
15031 		  && code != OMP_FOR
15032 		  && code != OACC_LOOP
15033 		  && code != OMP_MASTER
15034 		  && code != OMP_TASKGROUP
15035 		  && code != OMP_ORDERED
15036 		  && code != OMP_PARALLEL
15037 		  && code != OMP_SCAN
15038 		  && code != OMP_SECTIONS
15039 		  && code != OMP_SECTION
15040 		  && code != OMP_SINGLE);
15041     }
15042 #endif
15043 
15044   /* Otherwise we're gimplifying a subexpression, so the resulting
15045      value is interesting.  If it's a valid operand that matches
15046      GIMPLE_TEST_F, we're done. Unless we are handling some
15047      post-effects internally; if that's the case, we need to copy into
15048      a temporary before adding the post-effects to POST_P.  */
15049   if (gimple_seq_empty_p (internal_post) && (*gimple_test_f) (*expr_p))
15050     goto out;
15051 
15052   /* Otherwise, we need to create a new temporary for the gimplified
15053      expression.  */
15054 
15055   /* We can't return an lvalue if we have an internal postqueue.  The
15056      object the lvalue refers to would (probably) be modified by the
15057      postqueue; we need to copy the value out first, which means an
15058      rvalue.  */
15059   if ((fallback & fb_lvalue)
15060       && gimple_seq_empty_p (internal_post)
15061       && is_gimple_addressable (*expr_p))
15062     {
15063       /* An lvalue will do.  Take the address of the expression, store it
15064 	 in a temporary, and replace the expression with an INDIRECT_REF of
15065 	 that temporary.  */
15066       tree ref_alias_type = reference_alias_ptr_type (*expr_p);
15067       unsigned int ref_align = get_object_alignment (*expr_p);
15068       tree ref_type = TREE_TYPE (*expr_p);
15069       tmp = build_fold_addr_expr_loc (input_location, *expr_p);
15070       gimplify_expr (&tmp, pre_p, post_p, is_gimple_reg, fb_rvalue);
15071       if (TYPE_ALIGN (ref_type) != ref_align)
15072 	ref_type = build_aligned_type (ref_type, ref_align);
15073       *expr_p = build2 (MEM_REF, ref_type,
15074 			tmp, build_zero_cst (ref_alias_type));
15075     }
15076   else if ((fallback & fb_rvalue) && is_gimple_reg_rhs_or_call (*expr_p))
15077     {
15078       /* An rvalue will do.  Assign the gimplified expression into a
15079 	 new temporary TMP and replace the original expression with
15080 	 TMP.  First, make sure that the expression has a type so that
15081 	 it can be assigned into a temporary.  */
15082       gcc_assert (!VOID_TYPE_P (TREE_TYPE (*expr_p)));
15083       *expr_p = get_formal_tmp_var (*expr_p, pre_p);
15084     }
15085   else
15086     {
15087 #ifdef ENABLE_GIMPLE_CHECKING
15088       if (!(fallback & fb_mayfail))
15089 	{
15090 	  fprintf (stderr, "gimplification failed:\n");
15091 	  print_generic_expr (stderr, *expr_p);
15092 	  debug_tree (*expr_p);
15093 	  internal_error ("gimplification failed");
15094 	}
15095 #endif
15096       gcc_assert (fallback & fb_mayfail);
15097 
15098       /* If this is an asm statement, and the user asked for the
15099 	 impossible, don't die.  Fail and let gimplify_asm_expr
15100 	 issue an error.  */
15101       ret = GS_ERROR;
15102       goto out;
15103     }
15104 
15105   /* Make sure the temporary matches our predicate.  */
15106   gcc_assert ((*gimple_test_f) (*expr_p));
15107 
15108   if (!gimple_seq_empty_p (internal_post))
15109     {
15110       annotate_all_with_location (internal_post, input_location);
15111       gimplify_seq_add_seq (pre_p, internal_post);
15112     }
15113 
15114  out:
15115   input_location = saved_location;
15116   return ret;
15117 }
15118 
15119 /* Like gimplify_expr but make sure the gimplified result is not itself
15120    a SSA name (but a decl if it were).  Temporaries required by
15121    evaluating *EXPR_P may be still SSA names.  */
15122 
15123 static enum gimplify_status
gimplify_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p,bool (* gimple_test_f)(tree),fallback_t fallback,bool allow_ssa)15124 gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
15125 	       bool (*gimple_test_f) (tree), fallback_t fallback,
15126 	       bool allow_ssa)
15127 {
15128   enum gimplify_status ret = gimplify_expr (expr_p, pre_p, post_p,
15129 					    gimple_test_f, fallback);
15130   if (! allow_ssa
15131       && TREE_CODE (*expr_p) == SSA_NAME)
15132     *expr_p = get_initialized_tmp_var (*expr_p, pre_p, NULL, false);
15133   return ret;
15134 }
15135 
15136 /* Look through TYPE for variable-sized objects and gimplify each such
15137    size that we find.  Add to LIST_P any statements generated.  */
15138 
15139 void
gimplify_type_sizes(tree type,gimple_seq * list_p)15140 gimplify_type_sizes (tree type, gimple_seq *list_p)
15141 {
15142   tree field, t;
15143 
15144   if (type == NULL || type == error_mark_node)
15145     return;
15146 
15147   /* We first do the main variant, then copy into any other variants.  */
15148   type = TYPE_MAIN_VARIANT (type);
15149 
15150   /* Avoid infinite recursion.  */
15151   if (TYPE_SIZES_GIMPLIFIED (type))
15152     return;
15153 
15154   TYPE_SIZES_GIMPLIFIED (type) = 1;
15155 
15156   switch (TREE_CODE (type))
15157     {
15158     case INTEGER_TYPE:
15159     case ENUMERAL_TYPE:
15160     case BOOLEAN_TYPE:
15161     case REAL_TYPE:
15162     case FIXED_POINT_TYPE:
15163       gimplify_one_sizepos (&TYPE_MIN_VALUE (type), list_p);
15164       gimplify_one_sizepos (&TYPE_MAX_VALUE (type), list_p);
15165 
15166       for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
15167 	{
15168 	  TYPE_MIN_VALUE (t) = TYPE_MIN_VALUE (type);
15169 	  TYPE_MAX_VALUE (t) = TYPE_MAX_VALUE (type);
15170 	}
15171       break;
15172 
15173     case ARRAY_TYPE:
15174       /* These types may not have declarations, so handle them here.  */
15175       gimplify_type_sizes (TREE_TYPE (type), list_p);
15176       gimplify_type_sizes (TYPE_DOMAIN (type), list_p);
15177       /* Ensure VLA bounds aren't removed, for -O0 they should be variables
15178 	 with assigned stack slots, for -O1+ -g they should be tracked
15179 	 by VTA.  */
15180       if (!(TYPE_NAME (type)
15181 	    && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
15182 	    && DECL_IGNORED_P (TYPE_NAME (type)))
15183 	  && TYPE_DOMAIN (type)
15184 	  && INTEGRAL_TYPE_P (TYPE_DOMAIN (type)))
15185 	{
15186 	  t = TYPE_MIN_VALUE (TYPE_DOMAIN (type));
15187 	  if (t && VAR_P (t) && DECL_ARTIFICIAL (t))
15188 	    DECL_IGNORED_P (t) = 0;
15189 	  t = TYPE_MAX_VALUE (TYPE_DOMAIN (type));
15190 	  if (t && VAR_P (t) && DECL_ARTIFICIAL (t))
15191 	    DECL_IGNORED_P (t) = 0;
15192 	}
15193       break;
15194 
15195     case RECORD_TYPE:
15196     case UNION_TYPE:
15197     case QUAL_UNION_TYPE:
15198       for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
15199 	if (TREE_CODE (field) == FIELD_DECL)
15200 	  {
15201 	    gimplify_one_sizepos (&DECL_FIELD_OFFSET (field), list_p);
15202 	    gimplify_one_sizepos (&DECL_SIZE (field), list_p);
15203 	    gimplify_one_sizepos (&DECL_SIZE_UNIT (field), list_p);
15204 	    gimplify_type_sizes (TREE_TYPE (field), list_p);
15205 	  }
15206       break;
15207 
15208     case POINTER_TYPE:
15209     case REFERENCE_TYPE:
15210 	/* We used to recurse on the pointed-to type here, which turned out to
15211 	   be incorrect because its definition might refer to variables not
15212 	   yet initialized at this point if a forward declaration is involved.
15213 
15214 	   It was actually useful for anonymous pointed-to types to ensure
15215 	   that the sizes evaluation dominates every possible later use of the
15216 	   values.  Restricting to such types here would be safe since there
15217 	   is no possible forward declaration around, but would introduce an
15218 	   undesirable middle-end semantic to anonymity.  We then defer to
15219 	   front-ends the responsibility of ensuring that the sizes are
15220 	   evaluated both early and late enough, e.g. by attaching artificial
15221 	   type declarations to the tree.  */
15222       break;
15223 
15224     default:
15225       break;
15226     }
15227 
15228   gimplify_one_sizepos (&TYPE_SIZE (type), list_p);
15229   gimplify_one_sizepos (&TYPE_SIZE_UNIT (type), list_p);
15230 
15231   for (t = TYPE_NEXT_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
15232     {
15233       TYPE_SIZE (t) = TYPE_SIZE (type);
15234       TYPE_SIZE_UNIT (t) = TYPE_SIZE_UNIT (type);
15235       TYPE_SIZES_GIMPLIFIED (t) = 1;
15236     }
15237 }
15238 
15239 /* A subroutine of gimplify_type_sizes to make sure that *EXPR_P,
15240    a size or position, has had all of its SAVE_EXPRs evaluated.
15241    We add any required statements to *STMT_P.  */
15242 
15243 void
gimplify_one_sizepos(tree * expr_p,gimple_seq * stmt_p)15244 gimplify_one_sizepos (tree *expr_p, gimple_seq *stmt_p)
15245 {
15246   tree expr = *expr_p;
15247 
15248   /* We don't do anything if the value isn't there, is constant, or contains
15249      A PLACEHOLDER_EXPR.  We also don't want to do anything if it's already
15250      a VAR_DECL.  If it's a VAR_DECL from another function, the gimplifier
15251      will want to replace it with a new variable, but that will cause problems
15252      if this type is from outside the function.  It's OK to have that here.  */
15253   if (expr == NULL_TREE
15254       || is_gimple_constant (expr)
15255       || TREE_CODE (expr) == VAR_DECL
15256       || CONTAINS_PLACEHOLDER_P (expr))
15257     return;
15258 
15259   *expr_p = unshare_expr (expr);
15260 
15261   /* SSA names in decl/type fields are a bad idea - they'll get reclaimed
15262      if the def vanishes.  */
15263   gimplify_expr (expr_p, stmt_p, NULL, is_gimple_val, fb_rvalue, false);
15264 
15265   /* If expr wasn't already is_gimple_sizepos or is_gimple_constant from the
15266      FE, ensure that it is a VAR_DECL, otherwise we might handle some decls
15267      as gimplify_vla_decl even when they would have all sizes INTEGER_CSTs.  */
15268   if (is_gimple_constant (*expr_p))
15269     *expr_p = get_initialized_tmp_var (*expr_p, stmt_p, NULL, false);
15270 }
15271 
15272 /* Gimplify the body of statements of FNDECL and return a GIMPLE_BIND node
15273    containing the sequence of corresponding GIMPLE statements.  If DO_PARMS
15274    is true, also gimplify the parameters.  */
15275 
15276 gbind *
gimplify_body(tree fndecl,bool do_parms)15277 gimplify_body (tree fndecl, bool do_parms)
15278 {
15279   location_t saved_location = input_location;
15280   gimple_seq parm_stmts, parm_cleanup = NULL, seq;
15281   gimple *outer_stmt;
15282   gbind *outer_bind;
15283 
15284   timevar_push (TV_TREE_GIMPLIFY);
15285 
15286   init_tree_ssa (cfun);
15287 
15288   /* Initialize for optimize_insn_for_s{ize,peed}_p possibly called during
15289      gimplification.  */
15290   default_rtl_profile ();
15291 
15292   gcc_assert (gimplify_ctxp == NULL);
15293   push_gimplify_context (true);
15294 
15295   if (flag_openacc || flag_openmp)
15296     {
15297       gcc_assert (gimplify_omp_ctxp == NULL);
15298       if (lookup_attribute ("omp declare target", DECL_ATTRIBUTES (fndecl)))
15299 	gimplify_omp_ctxp = new_omp_context (ORT_IMPLICIT_TARGET);
15300     }
15301 
15302   /* Unshare most shared trees in the body and in that of any nested functions.
15303      It would seem we don't have to do this for nested functions because
15304      they are supposed to be output and then the outer function gimplified
15305      first, but the g++ front end doesn't always do it that way.  */
15306   unshare_body (fndecl);
15307   unvisit_body (fndecl);
15308 
15309   /* Make sure input_location isn't set to something weird.  */
15310   input_location = DECL_SOURCE_LOCATION (fndecl);
15311 
15312   /* Resolve callee-copies.  This has to be done before processing
15313      the body so that DECL_VALUE_EXPR gets processed correctly.  */
15314   parm_stmts = do_parms ? gimplify_parameters (&parm_cleanup) : NULL;
15315 
15316   /* Gimplify the function's body.  */
15317   seq = NULL;
15318   gimplify_stmt (&DECL_SAVED_TREE (fndecl), &seq);
15319   outer_stmt = gimple_seq_first_nondebug_stmt (seq);
15320   if (!outer_stmt)
15321     {
15322       outer_stmt = gimple_build_nop ();
15323       gimplify_seq_add_stmt (&seq, outer_stmt);
15324     }
15325 
15326   /* The body must contain exactly one statement, a GIMPLE_BIND.  If this is
15327      not the case, wrap everything in a GIMPLE_BIND to make it so.  */
15328   if (gimple_code (outer_stmt) == GIMPLE_BIND
15329       && (gimple_seq_first_nondebug_stmt (seq)
15330 	  == gimple_seq_last_nondebug_stmt (seq)))
15331     {
15332       outer_bind = as_a <gbind *> (outer_stmt);
15333       if (gimple_seq_first_stmt (seq) != outer_stmt
15334 	  || gimple_seq_last_stmt (seq) != outer_stmt)
15335 	{
15336 	  /* If there are debug stmts before or after outer_stmt, move them
15337 	     inside of outer_bind body.  */
15338 	  gimple_stmt_iterator gsi = gsi_for_stmt (outer_stmt, &seq);
15339 	  gimple_seq second_seq = NULL;
15340 	  if (gimple_seq_first_stmt (seq) != outer_stmt
15341 	      && gimple_seq_last_stmt (seq) != outer_stmt)
15342 	    {
15343 	      second_seq = gsi_split_seq_after (gsi);
15344 	      gsi_remove (&gsi, false);
15345 	    }
15346 	  else if (gimple_seq_first_stmt (seq) != outer_stmt)
15347 	    gsi_remove (&gsi, false);
15348 	  else
15349 	    {
15350 	      gsi_remove (&gsi, false);
15351 	      second_seq = seq;
15352 	      seq = NULL;
15353 	    }
15354 	  gimple_seq_add_seq_without_update (&seq,
15355 					     gimple_bind_body (outer_bind));
15356 	  gimple_seq_add_seq_without_update (&seq, second_seq);
15357 	  gimple_bind_set_body (outer_bind, seq);
15358 	}
15359     }
15360   else
15361     outer_bind = gimple_build_bind (NULL_TREE, seq, NULL);
15362 
15363   DECL_SAVED_TREE (fndecl) = NULL_TREE;
15364 
15365   /* If we had callee-copies statements, insert them at the beginning
15366      of the function and clear DECL_VALUE_EXPR_P on the parameters.  */
15367   if (!gimple_seq_empty_p (parm_stmts))
15368     {
15369       tree parm;
15370 
15371       gimplify_seq_add_seq (&parm_stmts, gimple_bind_body (outer_bind));
15372       if (parm_cleanup)
15373 	{
15374 	  gtry *g = gimple_build_try (parm_stmts, parm_cleanup,
15375 				      GIMPLE_TRY_FINALLY);
15376 	  parm_stmts = NULL;
15377 	  gimple_seq_add_stmt (&parm_stmts, g);
15378 	}
15379       gimple_bind_set_body (outer_bind, parm_stmts);
15380 
15381       for (parm = DECL_ARGUMENTS (current_function_decl);
15382 	   parm; parm = DECL_CHAIN (parm))
15383 	if (DECL_HAS_VALUE_EXPR_P (parm))
15384 	  {
15385 	    DECL_HAS_VALUE_EXPR_P (parm) = 0;
15386 	    DECL_IGNORED_P (parm) = 0;
15387 	  }
15388     }
15389 
15390   if ((flag_openacc || flag_openmp || flag_openmp_simd)
15391       && gimplify_omp_ctxp)
15392     {
15393       delete_omp_context (gimplify_omp_ctxp);
15394       gimplify_omp_ctxp = NULL;
15395     }
15396 
15397   pop_gimplify_context (outer_bind);
15398   gcc_assert (gimplify_ctxp == NULL);
15399 
15400   if (flag_checking && !seen_error ())
15401     verify_gimple_in_seq (gimple_bind_body (outer_bind));
15402 
15403   timevar_pop (TV_TREE_GIMPLIFY);
15404   input_location = saved_location;
15405 
15406   return outer_bind;
15407 }
15408 
15409 typedef char *char_p; /* For DEF_VEC_P.  */
15410 
15411 /* Return whether we should exclude FNDECL from instrumentation.  */
15412 
15413 static bool
flag_instrument_functions_exclude_p(tree fndecl)15414 flag_instrument_functions_exclude_p (tree fndecl)
15415 {
15416   vec<char_p> *v;
15417 
15418   v = (vec<char_p> *) flag_instrument_functions_exclude_functions;
15419   if (v && v->length () > 0)
15420     {
15421       const char *name;
15422       int i;
15423       char *s;
15424 
15425       name = lang_hooks.decl_printable_name (fndecl, 1);
15426       FOR_EACH_VEC_ELT (*v, i, s)
15427 	if (strstr (name, s) != NULL)
15428 	  return true;
15429     }
15430 
15431   v = (vec<char_p> *) flag_instrument_functions_exclude_files;
15432   if (v && v->length () > 0)
15433     {
15434       const char *name;
15435       int i;
15436       char *s;
15437 
15438       name = DECL_SOURCE_FILE (fndecl);
15439       FOR_EACH_VEC_ELT (*v, i, s)
15440 	if (strstr (name, s) != NULL)
15441 	  return true;
15442     }
15443 
15444   return false;
15445 }
15446 
15447 /* Entry point to the gimplification pass.  FNDECL is the FUNCTION_DECL
15448    node for the function we want to gimplify.
15449 
15450    Return the sequence of GIMPLE statements corresponding to the body
15451    of FNDECL.  */
15452 
15453 void
gimplify_function_tree(tree fndecl)15454 gimplify_function_tree (tree fndecl)
15455 {
15456   gimple_seq seq;
15457   gbind *bind;
15458 
15459   gcc_assert (!gimple_body (fndecl));
15460 
15461   if (DECL_STRUCT_FUNCTION (fndecl))
15462     push_cfun (DECL_STRUCT_FUNCTION (fndecl));
15463   else
15464     push_struct_function (fndecl);
15465 
15466   /* Tentatively set PROP_gimple_lva here, and reset it in gimplify_va_arg_expr
15467      if necessary.  */
15468   cfun->curr_properties |= PROP_gimple_lva;
15469 
15470   if (asan_sanitize_use_after_scope ())
15471     asan_poisoned_variables = new hash_set<tree> ();
15472   bind = gimplify_body (fndecl, true);
15473   if (asan_poisoned_variables)
15474     {
15475       delete asan_poisoned_variables;
15476       asan_poisoned_variables = NULL;
15477     }
15478 
15479   /* The tree body of the function is no longer needed, replace it
15480      with the new GIMPLE body.  */
15481   seq = NULL;
15482   gimple_seq_add_stmt (&seq, bind);
15483   gimple_set_body (fndecl, seq);
15484 
15485   /* If we're instrumenting function entry/exit, then prepend the call to
15486      the entry hook and wrap the whole function in a TRY_FINALLY_EXPR to
15487      catch the exit hook.  */
15488   /* ??? Add some way to ignore exceptions for this TFE.  */
15489   if (flag_instrument_function_entry_exit
15490       && !DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (fndecl)
15491       /* Do not instrument extern inline functions.  */
15492       && !(DECL_DECLARED_INLINE_P (fndecl)
15493 	   && DECL_EXTERNAL (fndecl)
15494 	   && DECL_DISREGARD_INLINE_LIMITS (fndecl))
15495       && !flag_instrument_functions_exclude_p (fndecl))
15496     {
15497       tree x;
15498       gbind *new_bind;
15499       gimple *tf;
15500       gimple_seq cleanup = NULL, body = NULL;
15501       tree tmp_var, this_fn_addr;
15502       gcall *call;
15503 
15504       /* The instrumentation hooks aren't going to call the instrumented
15505 	 function and the address they receive is expected to be matchable
15506 	 against symbol addresses.  Make sure we don't create a trampoline,
15507 	 in case the current function is nested.  */
15508       this_fn_addr = build_fold_addr_expr (current_function_decl);
15509       TREE_NO_TRAMPOLINE (this_fn_addr) = 1;
15510 
15511       x = builtin_decl_implicit (BUILT_IN_RETURN_ADDRESS);
15512       call = gimple_build_call (x, 1, integer_zero_node);
15513       tmp_var = create_tmp_var (ptr_type_node, "return_addr");
15514       gimple_call_set_lhs (call, tmp_var);
15515       gimplify_seq_add_stmt (&cleanup, call);
15516       x = builtin_decl_implicit (BUILT_IN_PROFILE_FUNC_EXIT);
15517       call = gimple_build_call (x, 2, this_fn_addr, tmp_var);
15518       gimplify_seq_add_stmt (&cleanup, call);
15519       tf = gimple_build_try (seq, cleanup, GIMPLE_TRY_FINALLY);
15520 
15521       x = builtin_decl_implicit (BUILT_IN_RETURN_ADDRESS);
15522       call = gimple_build_call (x, 1, integer_zero_node);
15523       tmp_var = create_tmp_var (ptr_type_node, "return_addr");
15524       gimple_call_set_lhs (call, tmp_var);
15525       gimplify_seq_add_stmt (&body, call);
15526       x = builtin_decl_implicit (BUILT_IN_PROFILE_FUNC_ENTER);
15527       call = gimple_build_call (x, 2, this_fn_addr, tmp_var);
15528       gimplify_seq_add_stmt (&body, call);
15529       gimplify_seq_add_stmt (&body, tf);
15530       new_bind = gimple_build_bind (NULL, body, NULL);
15531 
15532       /* Replace the current function body with the body
15533          wrapped in the try/finally TF.  */
15534       seq = NULL;
15535       gimple_seq_add_stmt (&seq, new_bind);
15536       gimple_set_body (fndecl, seq);
15537       bind = new_bind;
15538     }
15539 
15540   if (sanitize_flags_p (SANITIZE_THREAD)
15541       && param_tsan_instrument_func_entry_exit)
15542     {
15543       gcall *call = gimple_build_call_internal (IFN_TSAN_FUNC_EXIT, 0);
15544       gimple *tf = gimple_build_try (seq, call, GIMPLE_TRY_FINALLY);
15545       gbind *new_bind = gimple_build_bind (NULL, tf, NULL);
15546       /* Replace the current function body with the body
15547 	 wrapped in the try/finally TF.  */
15548       seq = NULL;
15549       gimple_seq_add_stmt (&seq, new_bind);
15550       gimple_set_body (fndecl, seq);
15551     }
15552 
15553   DECL_SAVED_TREE (fndecl) = NULL_TREE;
15554   cfun->curr_properties |= PROP_gimple_any;
15555 
15556   pop_cfun ();
15557 
15558   dump_function (TDI_gimple, fndecl);
15559 }
15560 
15561 /* Return a dummy expression of type TYPE in order to keep going after an
15562    error.  */
15563 
15564 static tree
dummy_object(tree type)15565 dummy_object (tree type)
15566 {
15567   tree t = build_int_cst (build_pointer_type (type), 0);
15568   return build2 (MEM_REF, type, t, t);
15569 }
15570 
15571 /* Gimplify __builtin_va_arg, aka VA_ARG_EXPR, which is not really a
15572    builtin function, but a very special sort of operator.  */
15573 
15574 enum gimplify_status
gimplify_va_arg_expr(tree * expr_p,gimple_seq * pre_p,gimple_seq * post_p ATTRIBUTE_UNUSED)15575 gimplify_va_arg_expr (tree *expr_p, gimple_seq *pre_p,
15576 		      gimple_seq *post_p ATTRIBUTE_UNUSED)
15577 {
15578   tree promoted_type, have_va_type;
15579   tree valist = TREE_OPERAND (*expr_p, 0);
15580   tree type = TREE_TYPE (*expr_p);
15581   tree t, tag, aptag;
15582   location_t loc = EXPR_LOCATION (*expr_p);
15583 
15584   /* Verify that valist is of the proper type.  */
15585   have_va_type = TREE_TYPE (valist);
15586   if (have_va_type == error_mark_node)
15587     return GS_ERROR;
15588   have_va_type = targetm.canonical_va_list_type (have_va_type);
15589   if (have_va_type == NULL_TREE
15590       && POINTER_TYPE_P (TREE_TYPE (valist)))
15591     /* Handle 'Case 1: Not an array type' from c-common.c/build_va_arg.  */
15592     have_va_type
15593       = targetm.canonical_va_list_type (TREE_TYPE (TREE_TYPE (valist)));
15594   gcc_assert (have_va_type != NULL_TREE);
15595 
15596   /* Generate a diagnostic for requesting data of a type that cannot
15597      be passed through `...' due to type promotion at the call site.  */
15598   if ((promoted_type = lang_hooks.types.type_promotes_to (type))
15599 	   != type)
15600     {
15601       static bool gave_help;
15602       bool warned;
15603       /* Use the expansion point to handle cases such as passing bool (defined
15604 	 in a system header) through `...'.  */
15605       location_t xloc
15606 	= expansion_point_location_if_in_system_header (loc);
15607 
15608       /* Unfortunately, this is merely undefined, rather than a constraint
15609 	 violation, so we cannot make this an error.  If this call is never
15610 	 executed, the program is still strictly conforming.  */
15611       auto_diagnostic_group d;
15612       warned = warning_at (xloc, 0,
15613 			   "%qT is promoted to %qT when passed through %<...%>",
15614 			   type, promoted_type);
15615       if (!gave_help && warned)
15616 	{
15617 	  gave_help = true;
15618 	  inform (xloc, "(so you should pass %qT not %qT to %<va_arg%>)",
15619 		  promoted_type, type);
15620 	}
15621 
15622       /* We can, however, treat "undefined" any way we please.
15623 	 Call abort to encourage the user to fix the program.  */
15624       if (warned)
15625 	inform (xloc, "if this code is reached, the program will abort");
15626       /* Before the abort, allow the evaluation of the va_list
15627 	 expression to exit or longjmp.  */
15628       gimplify_and_add (valist, pre_p);
15629       t = build_call_expr_loc (loc,
15630 			       builtin_decl_implicit (BUILT_IN_TRAP), 0);
15631       gimplify_and_add (t, pre_p);
15632 
15633       /* This is dead code, but go ahead and finish so that the
15634 	 mode of the result comes out right.  */
15635       *expr_p = dummy_object (type);
15636       return GS_ALL_DONE;
15637     }
15638 
15639   tag = build_int_cst (build_pointer_type (type), 0);
15640   aptag = build_int_cst (TREE_TYPE (valist), 0);
15641 
15642   *expr_p = build_call_expr_internal_loc (loc, IFN_VA_ARG, type, 3,
15643 					  valist, tag, aptag);
15644 
15645   /* Clear the tentatively set PROP_gimple_lva, to indicate that IFN_VA_ARG
15646      needs to be expanded.  */
15647   cfun->curr_properties &= ~PROP_gimple_lva;
15648 
15649   return GS_OK;
15650 }
15651 
15652 /* Build a new GIMPLE_ASSIGN tuple and append it to the end of *SEQ_P.
15653 
15654    DST/SRC are the destination and source respectively.  You can pass
15655    ungimplified trees in DST or SRC, in which case they will be
15656    converted to a gimple operand if necessary.
15657 
15658    This function returns the newly created GIMPLE_ASSIGN tuple.  */
15659 
15660 gimple *
gimplify_assign(tree dst,tree src,gimple_seq * seq_p)15661 gimplify_assign (tree dst, tree src, gimple_seq *seq_p)
15662 {
15663   tree t = build2 (MODIFY_EXPR, TREE_TYPE (dst), dst, src);
15664   gimplify_and_add (t, seq_p);
15665   ggc_free (t);
15666   return gimple_seq_last_stmt (*seq_p);
15667 }
15668 
15669 inline hashval_t
hash(const elt_t * p)15670 gimplify_hasher::hash (const elt_t *p)
15671 {
15672   tree t = p->val;
15673   return iterative_hash_expr (t, 0);
15674 }
15675 
15676 inline bool
equal(const elt_t * p1,const elt_t * p2)15677 gimplify_hasher::equal (const elt_t *p1, const elt_t *p2)
15678 {
15679   tree t1 = p1->val;
15680   tree t2 = p2->val;
15681   enum tree_code code = TREE_CODE (t1);
15682 
15683   if (TREE_CODE (t2) != code
15684       || TREE_TYPE (t1) != TREE_TYPE (t2))
15685     return false;
15686 
15687   if (!operand_equal_p (t1, t2, 0))
15688     return false;
15689 
15690   /* Only allow them to compare equal if they also hash equal; otherwise
15691      results are nondeterminate, and we fail bootstrap comparison.  */
15692   gcc_checking_assert (hash (p1) == hash (p2));
15693 
15694   return true;
15695 }
15696