libcpp, c, middle-end: Optimize initializers using #embed in C
[official-gcc.git] / gcc / tree-ssa-forwprop.cc
blob766eaf0e4e79f097ee43e8832355d069337c5d18
1 /* Forward propagation of expressions for single use variables.
2 Copyright (C) 2004-2024 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3, or (at your option)
9 any later version.
11 GCC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3. If not see
18 <http://www.gnu.org/licenses/>. */
20 #include "config.h"
21 #include "system.h"
22 #include "coretypes.h"
23 #include "backend.h"
24 #include "rtl.h"
25 #include "tree.h"
26 #include "gimple.h"
27 #include "cfghooks.h"
28 #include "tree-pass.h"
29 #include "ssa.h"
30 #include "expmed.h"
31 #include "optabs-query.h"
32 #include "gimple-pretty-print.h"
33 #include "fold-const.h"
34 #include "stor-layout.h"
35 #include "gimple-iterator.h"
36 #include "gimple-fold.h"
37 #include "tree-eh.h"
38 #include "gimplify.h"
39 #include "gimplify-me.h"
40 #include "tree-cfg.h"
41 #include "expr.h"
42 #include "tree-dfa.h"
43 #include "tree-ssa-propagate.h"
44 #include "tree-ssa-dom.h"
45 #include "tree-ssa-strlen.h"
46 #include "builtins.h"
47 #include "tree-cfgcleanup.h"
48 #include "cfganal.h"
49 #include "optabs-tree.h"
50 #include "insn-config.h"
51 #include "recog.h"
52 #include "tree-vector-builder.h"
53 #include "vec-perm-indices.h"
54 #include "internal-fn.h"
55 #include "cgraph.h"
56 #include "tree-ssa.h"
57 #include "gimple-range.h"
58 #include "tree-ssa-dce.h"
60 /* This pass propagates the RHS of assignment statements into use
61 sites of the LHS of the assignment. It's basically a specialized
62 form of tree combination. It is hoped all of this can disappear
63 when we have a generalized tree combiner.
65 One class of common cases we handle is forward propagating a single use
66 variable into a COND_EXPR.
68 bb0:
69 x = a COND b;
70 if (x) goto ... else goto ...
72 Will be transformed into:
74 bb0:
75 if (a COND b) goto ... else goto ...
77 Similarly for the tests (x == 0), (x != 0), (x == 1) and (x != 1).
79 Or (assuming c1 and c2 are constants):
81 bb0:
82 x = a + c1;
83 if (x EQ/NEQ c2) goto ... else goto ...
85 Will be transformed into:
87 bb0:
88 if (a EQ/NEQ (c2 - c1)) goto ... else goto ...
90 Similarly for x = a - c1.
94 bb0:
95 x = !a
96 if (x) goto ... else goto ...
98 Will be transformed into:
100 bb0:
101 if (a == 0) goto ... else goto ...
103 Similarly for the tests (x == 0), (x != 0), (x == 1) and (x != 1).
104 For these cases, we propagate A into all, possibly more than one,
105 COND_EXPRs that use X.
109 bb0:
110 x = (typecast) a
111 if (x) goto ... else goto ...
113 Will be transformed into:
115 bb0:
116 if (a != 0) goto ... else goto ...
118 (Assuming a is an integral type and x is a boolean or x is an
119 integral and a is a boolean.)
121 Similarly for the tests (x == 0), (x != 0), (x == 1) and (x != 1).
122 For these cases, we propagate A into all, possibly more than one,
123 COND_EXPRs that use X.
125 In addition to eliminating the variable and the statement which assigns
126 a value to the variable, we may be able to later thread the jump without
127 adding insane complexity in the dominator optimizer.
129 Also note these transformations can cascade. We handle this by having
130 a worklist of COND_EXPR statements to examine. As we make a change to
131 a statement, we put it back on the worklist to examine on the next
132 iteration of the main loop.
134 A second class of propagation opportunities arises for ADDR_EXPR
135 nodes.
137 ptr = &x->y->z;
138 res = *ptr;
140 Will get turned into
142 res = x->y->z;
145 ptr = (type1*)&type2var;
146 res = *ptr
148 Will get turned into (if type1 and type2 are the same size
149 and neither have volatile on them):
150 res = VIEW_CONVERT_EXPR<type1>(type2var)
154 ptr = &x[0];
155 ptr2 = ptr + <constant>;
157 Will get turned into
159 ptr2 = &x[constant/elementsize];
163 ptr = &x[0];
164 offset = index * element_size;
165 offset_p = (pointer) offset;
166 ptr2 = ptr + offset_p
168 Will get turned into:
170 ptr2 = &x[index];
173 ssa = (int) decl
174 res = ssa & 1
176 Provided that decl has known alignment >= 2, will get turned into
178 res = 0
180 We also propagate casts into SWITCH_EXPR and COND_EXPR conditions to
181 allow us to remove the cast and {NOT_EXPR,NEG_EXPR} into a subsequent
182 {NOT_EXPR,NEG_EXPR}.
184 This will (of course) be extended as other needs arise. */
186 static bool forward_propagate_addr_expr (tree, tree, bool);
188 /* Set to true if we delete dead edges during the optimization. */
189 static bool cfg_changed;
191 static tree rhs_to_tree (tree type, gimple *stmt);
193 static bitmap to_purge;
195 /* Const-and-copy lattice. */
196 static vec<tree> lattice;
198 /* Set the lattice entry for NAME to VAL. */
199 static void
200 fwprop_set_lattice_val (tree name, tree val)
202 if (TREE_CODE (name) == SSA_NAME)
204 if (SSA_NAME_VERSION (name) >= lattice.length ())
206 lattice.reserve (num_ssa_names - lattice.length ());
207 lattice.quick_grow_cleared (num_ssa_names);
209 lattice[SSA_NAME_VERSION (name)] = val;
210 /* As this now constitutes a copy duplicate points-to
211 and range info appropriately. */
212 if (TREE_CODE (val) == SSA_NAME)
213 maybe_duplicate_ssa_info_at_copy (name, val);
217 /* Invalidate the lattice entry for NAME, done when releasing SSA names. */
218 static void
219 fwprop_invalidate_lattice (tree name)
221 if (name
222 && TREE_CODE (name) == SSA_NAME
223 && SSA_NAME_VERSION (name) < lattice.length ())
224 lattice[SSA_NAME_VERSION (name)] = NULL_TREE;
228 /* Get the statement we can propagate from into NAME skipping
229 trivial copies. Returns the statement which defines the
230 propagation source or NULL_TREE if there is no such one.
231 If SINGLE_USE_ONLY is set considers only sources which have
232 a single use chain up to NAME. If SINGLE_USE_P is non-null,
233 it is set to whether the chain to NAME is a single use chain
234 or not. SINGLE_USE_P is not written to if SINGLE_USE_ONLY is set. */
236 static gimple *
237 get_prop_source_stmt (tree name, bool single_use_only, bool *single_use_p)
239 bool single_use = true;
241 do {
242 gimple *def_stmt = SSA_NAME_DEF_STMT (name);
244 if (!has_single_use (name))
246 single_use = false;
247 if (single_use_only)
248 return NULL;
251 /* If name is defined by a PHI node or is the default def, bail out. */
252 if (!is_gimple_assign (def_stmt))
253 return NULL;
255 /* If def_stmt is a simple copy, continue looking. */
256 if (gimple_assign_rhs_code (def_stmt) == SSA_NAME)
257 name = gimple_assign_rhs1 (def_stmt);
258 else
260 if (!single_use_only && single_use_p)
261 *single_use_p = single_use;
263 return def_stmt;
265 } while (1);
268 /* Checks if the destination ssa name in DEF_STMT can be used as
269 propagation source. Returns true if so, otherwise false. */
271 static bool
272 can_propagate_from (gimple *def_stmt)
274 gcc_assert (is_gimple_assign (def_stmt));
276 /* If the rhs has side-effects we cannot propagate from it. */
277 if (gimple_has_volatile_ops (def_stmt))
278 return false;
280 /* If the rhs is a load we cannot propagate from it. */
281 if (TREE_CODE_CLASS (gimple_assign_rhs_code (def_stmt)) == tcc_reference
282 || TREE_CODE_CLASS (gimple_assign_rhs_code (def_stmt)) == tcc_declaration)
283 return false;
285 /* Constants can be always propagated. */
286 if (gimple_assign_single_p (def_stmt)
287 && is_gimple_min_invariant (gimple_assign_rhs1 (def_stmt)))
288 return true;
290 /* We cannot propagate ssa names that occur in abnormal phi nodes. */
291 if (stmt_references_abnormal_ssa_name (def_stmt))
292 return false;
294 /* If the definition is a conversion of a pointer to a function type,
295 then we cannot apply optimizations as some targets require
296 function pointers to be canonicalized and in this case this
297 optimization could eliminate a necessary canonicalization. */
298 if (CONVERT_EXPR_CODE_P (gimple_assign_rhs_code (def_stmt)))
300 tree rhs = gimple_assign_rhs1 (def_stmt);
301 if (FUNCTION_POINTER_TYPE_P (TREE_TYPE (rhs)))
302 return false;
305 return true;
308 /* Remove a chain of dead statements starting at the definition of
309 NAME. The chain is linked via the first operand of the defining statements.
310 If NAME was replaced in its only use then this function can be used
311 to clean up dead stmts. The function handles already released SSA
312 names gracefully.
313 Returns true if cleanup-cfg has to run. */
315 static bool
316 remove_prop_source_from_use (tree name)
318 gimple_stmt_iterator gsi;
319 gimple *stmt;
320 bool cfg_changed = false;
322 do {
323 basic_block bb;
325 if (SSA_NAME_IN_FREE_LIST (name)
326 || SSA_NAME_IS_DEFAULT_DEF (name)
327 || !has_zero_uses (name))
328 return cfg_changed;
330 stmt = SSA_NAME_DEF_STMT (name);
331 if (gimple_code (stmt) == GIMPLE_PHI
332 || gimple_has_side_effects (stmt))
333 return cfg_changed;
335 bb = gimple_bb (stmt);
336 gsi = gsi_for_stmt (stmt);
337 unlink_stmt_vdef (stmt);
338 if (gsi_remove (&gsi, true))
339 bitmap_set_bit (to_purge, bb->index);
340 fwprop_invalidate_lattice (gimple_get_lhs (stmt));
341 release_defs (stmt);
343 name = is_gimple_assign (stmt) ? gimple_assign_rhs1 (stmt) : NULL_TREE;
344 } while (name && TREE_CODE (name) == SSA_NAME);
346 return cfg_changed;
349 /* Return the rhs of a gassign *STMT in a form of a single tree,
350 converted to type TYPE.
352 This should disappear, but is needed so we can combine expressions and use
353 the fold() interfaces. Long term, we need to develop folding and combine
354 routines that deal with gimple exclusively . */
356 static tree
357 rhs_to_tree (tree type, gimple *stmt)
359 location_t loc = gimple_location (stmt);
360 enum tree_code code = gimple_assign_rhs_code (stmt);
361 switch (get_gimple_rhs_class (code))
363 case GIMPLE_TERNARY_RHS:
364 return fold_build3_loc (loc, code, type, gimple_assign_rhs1 (stmt),
365 gimple_assign_rhs2 (stmt),
366 gimple_assign_rhs3 (stmt));
367 case GIMPLE_BINARY_RHS:
368 return fold_build2_loc (loc, code, type, gimple_assign_rhs1 (stmt),
369 gimple_assign_rhs2 (stmt));
370 case GIMPLE_UNARY_RHS:
371 return build1 (code, type, gimple_assign_rhs1 (stmt));
372 case GIMPLE_SINGLE_RHS:
373 return gimple_assign_rhs1 (stmt);
374 default:
375 gcc_unreachable ();
379 /* Combine OP0 CODE OP1 in the context of a COND_EXPR. Returns
380 the folded result in a form suitable for COND_EXPR_COND or
381 NULL_TREE, if there is no suitable simplified form. If
382 INVARIANT_ONLY is true only gimple_min_invariant results are
383 considered simplified. */
385 static tree
386 combine_cond_expr_cond (gimple *stmt, enum tree_code code, tree type,
387 tree op0, tree op1, bool invariant_only)
389 tree t;
391 gcc_assert (TREE_CODE_CLASS (code) == tcc_comparison);
393 fold_defer_overflow_warnings ();
394 t = fold_binary_loc (gimple_location (stmt), code, type, op0, op1);
395 if (!t)
397 fold_undefer_overflow_warnings (false, NULL, 0);
398 return NULL_TREE;
401 /* Require that we got a boolean type out if we put one in. */
402 gcc_assert (TREE_CODE (TREE_TYPE (t)) == TREE_CODE (type));
404 /* Canonicalize the combined condition for use in a COND_EXPR. */
405 t = canonicalize_cond_expr_cond (t);
407 /* Bail out if we required an invariant but didn't get one. */
408 if (!t || (invariant_only && !is_gimple_min_invariant (t)))
410 fold_undefer_overflow_warnings (false, NULL, 0);
411 return NULL_TREE;
414 bool nowarn = warning_suppressed_p (stmt, OPT_Wstrict_overflow);
415 fold_undefer_overflow_warnings (!nowarn, stmt, 0);
417 return t;
420 /* Combine the comparison OP0 CODE OP1 at LOC with the defining statements
421 of its operand. Return a new comparison tree or NULL_TREE if there
422 were no simplifying combines. */
424 static tree
425 forward_propagate_into_comparison_1 (gimple *stmt,
426 enum tree_code code, tree type,
427 tree op0, tree op1)
429 tree tmp = NULL_TREE;
430 tree rhs0 = NULL_TREE, rhs1 = NULL_TREE;
431 bool single_use0_p = false, single_use1_p = false;
433 /* For comparisons use the first operand, that is likely to
434 simplify comparisons against constants. */
435 if (TREE_CODE (op0) == SSA_NAME)
437 gimple *def_stmt = get_prop_source_stmt (op0, false, &single_use0_p);
438 if (def_stmt && can_propagate_from (def_stmt))
440 enum tree_code def_code = gimple_assign_rhs_code (def_stmt);
441 bool invariant_only_p = !single_use0_p;
443 rhs0 = rhs_to_tree (TREE_TYPE (op1), def_stmt);
445 /* Always combine comparisons or conversions from booleans. */
446 if (TREE_CODE (op1) == INTEGER_CST
447 && ((CONVERT_EXPR_CODE_P (def_code)
448 && TREE_CODE (TREE_TYPE (TREE_OPERAND (rhs0, 0)))
449 == BOOLEAN_TYPE)
450 || TREE_CODE_CLASS (def_code) == tcc_comparison))
451 invariant_only_p = false;
453 tmp = combine_cond_expr_cond (stmt, code, type,
454 rhs0, op1, invariant_only_p);
455 if (tmp)
456 return tmp;
460 /* If that wasn't successful, try the second operand. */
461 if (TREE_CODE (op1) == SSA_NAME)
463 gimple *def_stmt = get_prop_source_stmt (op1, false, &single_use1_p);
464 if (def_stmt && can_propagate_from (def_stmt))
466 rhs1 = rhs_to_tree (TREE_TYPE (op0), def_stmt);
467 tmp = combine_cond_expr_cond (stmt, code, type,
468 op0, rhs1, !single_use1_p);
469 if (tmp)
470 return tmp;
474 /* If that wasn't successful either, try both operands. */
475 if (rhs0 != NULL_TREE
476 && rhs1 != NULL_TREE)
477 tmp = combine_cond_expr_cond (stmt, code, type,
478 rhs0, rhs1,
479 !(single_use0_p && single_use1_p));
481 return tmp;
484 /* Propagate from the ssa name definition statements of the assignment
485 from a comparison at *GSI into the conditional if that simplifies it.
486 Returns 1 if the stmt was modified and 2 if the CFG needs cleanup,
487 otherwise returns 0. */
489 static int
490 forward_propagate_into_comparison (gimple_stmt_iterator *gsi)
492 gimple *stmt = gsi_stmt (*gsi);
493 tree tmp;
494 bool cfg_changed = false;
495 tree type = TREE_TYPE (gimple_assign_lhs (stmt));
496 tree rhs1 = gimple_assign_rhs1 (stmt);
497 tree rhs2 = gimple_assign_rhs2 (stmt);
499 /* Combine the comparison with defining statements. */
500 tmp = forward_propagate_into_comparison_1 (stmt,
501 gimple_assign_rhs_code (stmt),
502 type, rhs1, rhs2);
503 if (tmp && useless_type_conversion_p (type, TREE_TYPE (tmp)))
505 gimple_assign_set_rhs_from_tree (gsi, tmp);
506 fold_stmt (gsi);
507 update_stmt (gsi_stmt (*gsi));
509 if (TREE_CODE (rhs1) == SSA_NAME)
510 cfg_changed |= remove_prop_source_from_use (rhs1);
511 if (TREE_CODE (rhs2) == SSA_NAME)
512 cfg_changed |= remove_prop_source_from_use (rhs2);
513 return cfg_changed ? 2 : 1;
516 return 0;
519 /* Propagate from the ssa name definition statements of COND_EXPR
520 in GIMPLE_COND statement STMT into the conditional if that simplifies it.
521 Returns zero if no statement was changed, one if there were
522 changes and two if cfg_cleanup needs to run. */
524 static int
525 forward_propagate_into_gimple_cond (gcond *stmt)
527 tree tmp;
528 enum tree_code code = gimple_cond_code (stmt);
529 bool cfg_changed = false;
530 tree rhs1 = gimple_cond_lhs (stmt);
531 tree rhs2 = gimple_cond_rhs (stmt);
533 /* We can do tree combining on SSA_NAME and comparison expressions. */
534 if (TREE_CODE_CLASS (gimple_cond_code (stmt)) != tcc_comparison)
535 return 0;
537 tmp = forward_propagate_into_comparison_1 (stmt, code,
538 boolean_type_node,
539 rhs1, rhs2);
540 if (tmp
541 && is_gimple_condexpr_for_cond (tmp))
543 if (dump_file)
545 fprintf (dump_file, " Replaced '");
546 print_gimple_expr (dump_file, stmt, 0);
547 fprintf (dump_file, "' with '");
548 print_generic_expr (dump_file, tmp);
549 fprintf (dump_file, "'\n");
552 gimple_cond_set_condition_from_tree (stmt, unshare_expr (tmp));
553 update_stmt (stmt);
555 if (TREE_CODE (rhs1) == SSA_NAME)
556 cfg_changed |= remove_prop_source_from_use (rhs1);
557 if (TREE_CODE (rhs2) == SSA_NAME)
558 cfg_changed |= remove_prop_source_from_use (rhs2);
559 return (cfg_changed || is_gimple_min_invariant (tmp)) ? 2 : 1;
562 /* Canonicalize _Bool == 0 and _Bool != 1 to _Bool != 0 by swapping edges. */
563 if ((TREE_CODE (TREE_TYPE (rhs1)) == BOOLEAN_TYPE
564 || (INTEGRAL_TYPE_P (TREE_TYPE (rhs1))
565 && TYPE_PRECISION (TREE_TYPE (rhs1)) == 1))
566 && ((code == EQ_EXPR
567 && integer_zerop (rhs2))
568 || (code == NE_EXPR
569 && integer_onep (rhs2))))
571 basic_block bb = gimple_bb (stmt);
572 gimple_cond_set_code (stmt, NE_EXPR);
573 gimple_cond_set_rhs (stmt, build_zero_cst (TREE_TYPE (rhs1)));
574 EDGE_SUCC (bb, 0)->flags ^= (EDGE_TRUE_VALUE|EDGE_FALSE_VALUE);
575 EDGE_SUCC (bb, 1)->flags ^= (EDGE_TRUE_VALUE|EDGE_FALSE_VALUE);
576 return 1;
579 return 0;
582 /* We've just substituted an ADDR_EXPR into stmt. Update all the
583 relevant data structures to match. */
585 static void
586 tidy_after_forward_propagate_addr (gimple *stmt)
588 /* We may have turned a trapping insn into a non-trapping insn. */
589 if (maybe_clean_or_replace_eh_stmt (stmt, stmt))
590 bitmap_set_bit (to_purge, gimple_bb (stmt)->index);
592 if (TREE_CODE (gimple_assign_rhs1 (stmt)) == ADDR_EXPR)
593 recompute_tree_invariant_for_addr_expr (gimple_assign_rhs1 (stmt));
596 /* NAME is a SSA_NAME representing DEF_RHS which is of the form
597 ADDR_EXPR <whatever>.
599 Try to forward propagate the ADDR_EXPR into the use USE_STMT.
600 Often this will allow for removal of an ADDR_EXPR and INDIRECT_REF
601 node or for recovery of array indexing from pointer arithmetic.
603 Return true if the propagation was successful (the propagation can
604 be not totally successful, yet things may have been changed). */
606 static bool
607 forward_propagate_addr_expr_1 (tree name, tree def_rhs,
608 gimple_stmt_iterator *use_stmt_gsi,
609 bool single_use_p)
611 tree lhs, rhs, rhs2, array_ref;
612 gimple *use_stmt = gsi_stmt (*use_stmt_gsi);
613 enum tree_code rhs_code;
614 bool res = true;
616 gcc_assert (TREE_CODE (def_rhs) == ADDR_EXPR);
618 lhs = gimple_assign_lhs (use_stmt);
619 rhs_code = gimple_assign_rhs_code (use_stmt);
620 rhs = gimple_assign_rhs1 (use_stmt);
622 /* Do not perform copy-propagation but recurse through copy chains. */
623 if (TREE_CODE (lhs) == SSA_NAME
624 && rhs_code == SSA_NAME)
625 return forward_propagate_addr_expr (lhs, def_rhs, single_use_p);
627 /* The use statement could be a conversion. Recurse to the uses of the
628 lhs as copyprop does not copy through pointer to integer to pointer
629 conversions and FRE does not catch all cases either.
630 Treat the case of a single-use name and
631 a conversion to def_rhs type separate, though. */
632 if (TREE_CODE (lhs) == SSA_NAME
633 && CONVERT_EXPR_CODE_P (rhs_code))
635 /* If there is a point in a conversion chain where the types match
636 so we can remove a conversion re-materialize the address here
637 and stop. */
638 if (single_use_p
639 && useless_type_conversion_p (TREE_TYPE (lhs), TREE_TYPE (def_rhs)))
641 gimple_assign_set_rhs1 (use_stmt, unshare_expr (def_rhs));
642 gimple_assign_set_rhs_code (use_stmt, TREE_CODE (def_rhs));
643 return true;
646 /* Else recurse if the conversion preserves the address value. */
647 if ((INTEGRAL_TYPE_P (TREE_TYPE (lhs))
648 || POINTER_TYPE_P (TREE_TYPE (lhs)))
649 && (TYPE_PRECISION (TREE_TYPE (lhs))
650 >= TYPE_PRECISION (TREE_TYPE (def_rhs))))
651 return forward_propagate_addr_expr (lhs, def_rhs, single_use_p);
653 return false;
656 /* If this isn't a conversion chain from this on we only can propagate
657 into compatible pointer contexts. */
658 if (!types_compatible_p (TREE_TYPE (name), TREE_TYPE (def_rhs)))
659 return false;
661 /* Propagate through constant pointer adjustments. */
662 if (TREE_CODE (lhs) == SSA_NAME
663 && rhs_code == POINTER_PLUS_EXPR
664 && rhs == name
665 && TREE_CODE (gimple_assign_rhs2 (use_stmt)) == INTEGER_CST)
667 tree new_def_rhs;
668 /* As we come here with non-invariant addresses in def_rhs we need
669 to make sure we can build a valid constant offsetted address
670 for further propagation. Simply rely on fold building that
671 and check after the fact. */
672 new_def_rhs = fold_build2 (MEM_REF, TREE_TYPE (TREE_TYPE (rhs)),
673 def_rhs,
674 fold_convert (ptr_type_node,
675 gimple_assign_rhs2 (use_stmt)));
676 if (TREE_CODE (new_def_rhs) == MEM_REF
677 && !is_gimple_mem_ref_addr (TREE_OPERAND (new_def_rhs, 0)))
678 return false;
679 new_def_rhs = build1 (ADDR_EXPR, TREE_TYPE (rhs), new_def_rhs);
681 /* Recurse. If we could propagate into all uses of lhs do not
682 bother to replace into the current use but just pretend we did. */
683 if (forward_propagate_addr_expr (lhs, new_def_rhs, single_use_p))
684 return true;
686 if (useless_type_conversion_p (TREE_TYPE (lhs),
687 TREE_TYPE (new_def_rhs)))
688 gimple_assign_set_rhs_with_ops (use_stmt_gsi, TREE_CODE (new_def_rhs),
689 new_def_rhs);
690 else if (is_gimple_min_invariant (new_def_rhs))
691 gimple_assign_set_rhs_with_ops (use_stmt_gsi, NOP_EXPR, new_def_rhs);
692 else
693 return false;
694 gcc_assert (gsi_stmt (*use_stmt_gsi) == use_stmt);
695 update_stmt (use_stmt);
696 return true;
699 /* Now strip away any outer COMPONENT_REF/ARRAY_REF nodes from the LHS.
700 ADDR_EXPR will not appear on the LHS. */
701 tree *lhsp = gimple_assign_lhs_ptr (use_stmt);
702 while (handled_component_p (*lhsp))
703 lhsp = &TREE_OPERAND (*lhsp, 0);
704 lhs = *lhsp;
706 /* Now see if the LHS node is a MEM_REF using NAME. If so,
707 propagate the ADDR_EXPR into the use of NAME and fold the result. */
708 if (TREE_CODE (lhs) == MEM_REF
709 && TREE_OPERAND (lhs, 0) == name)
711 tree def_rhs_base;
712 poly_int64 def_rhs_offset;
713 /* If the address is invariant we can always fold it. */
714 if ((def_rhs_base = get_addr_base_and_unit_offset (TREE_OPERAND (def_rhs, 0),
715 &def_rhs_offset)))
717 poly_offset_int off = mem_ref_offset (lhs);
718 tree new_ptr;
719 off += def_rhs_offset;
720 if (TREE_CODE (def_rhs_base) == MEM_REF)
722 off += mem_ref_offset (def_rhs_base);
723 new_ptr = TREE_OPERAND (def_rhs_base, 0);
725 else
726 new_ptr = build_fold_addr_expr (def_rhs_base);
727 TREE_OPERAND (lhs, 0) = new_ptr;
728 TREE_OPERAND (lhs, 1)
729 = wide_int_to_tree (TREE_TYPE (TREE_OPERAND (lhs, 1)), off);
730 tidy_after_forward_propagate_addr (use_stmt);
731 /* Continue propagating into the RHS if this was not the only use. */
732 if (single_use_p)
733 return true;
735 /* If the LHS is a plain dereference and the value type is the same as
736 that of the pointed-to type of the address we can put the
737 dereferenced address on the LHS preserving the original alias-type. */
738 else if (integer_zerop (TREE_OPERAND (lhs, 1))
739 && ((gimple_assign_lhs (use_stmt) == lhs
740 && useless_type_conversion_p
741 (TREE_TYPE (TREE_OPERAND (def_rhs, 0)),
742 TREE_TYPE (gimple_assign_rhs1 (use_stmt))))
743 || types_compatible_p (TREE_TYPE (lhs),
744 TREE_TYPE (TREE_OPERAND (def_rhs, 0))))
745 /* Don't forward anything into clobber stmts if it would result
746 in the lhs no longer being a MEM_REF. */
747 && (!gimple_clobber_p (use_stmt)
748 || TREE_CODE (TREE_OPERAND (def_rhs, 0)) == MEM_REF))
750 tree *def_rhs_basep = &TREE_OPERAND (def_rhs, 0);
751 tree new_offset, new_base, saved, new_lhs;
752 while (handled_component_p (*def_rhs_basep))
753 def_rhs_basep = &TREE_OPERAND (*def_rhs_basep, 0);
754 saved = *def_rhs_basep;
755 if (TREE_CODE (*def_rhs_basep) == MEM_REF)
757 new_base = TREE_OPERAND (*def_rhs_basep, 0);
758 new_offset = fold_convert (TREE_TYPE (TREE_OPERAND (lhs, 1)),
759 TREE_OPERAND (*def_rhs_basep, 1));
761 else
763 new_base = build_fold_addr_expr (*def_rhs_basep);
764 new_offset = TREE_OPERAND (lhs, 1);
766 *def_rhs_basep = build2 (MEM_REF, TREE_TYPE (*def_rhs_basep),
767 new_base, new_offset);
768 TREE_THIS_VOLATILE (*def_rhs_basep) = TREE_THIS_VOLATILE (lhs);
769 TREE_SIDE_EFFECTS (*def_rhs_basep) = TREE_SIDE_EFFECTS (lhs);
770 TREE_THIS_NOTRAP (*def_rhs_basep) = TREE_THIS_NOTRAP (lhs);
771 new_lhs = unshare_expr (TREE_OPERAND (def_rhs, 0));
772 *lhsp = new_lhs;
773 TREE_THIS_VOLATILE (new_lhs) = TREE_THIS_VOLATILE (lhs);
774 TREE_SIDE_EFFECTS (new_lhs) = TREE_SIDE_EFFECTS (lhs);
775 *def_rhs_basep = saved;
776 tidy_after_forward_propagate_addr (use_stmt);
777 /* Continue propagating into the RHS if this was not the
778 only use. */
779 if (single_use_p)
780 return true;
782 else
783 /* We can have a struct assignment dereferencing our name twice.
784 Note that we didn't propagate into the lhs to not falsely
785 claim we did when propagating into the rhs. */
786 res = false;
789 /* Strip away any outer COMPONENT_REF, ARRAY_REF or ADDR_EXPR
790 nodes from the RHS. */
791 tree *rhsp = gimple_assign_rhs1_ptr (use_stmt);
792 if (TREE_CODE (*rhsp) == ADDR_EXPR)
793 rhsp = &TREE_OPERAND (*rhsp, 0);
794 while (handled_component_p (*rhsp))
795 rhsp = &TREE_OPERAND (*rhsp, 0);
796 rhs = *rhsp;
798 /* Now see if the RHS node is a MEM_REF using NAME. If so,
799 propagate the ADDR_EXPR into the use of NAME and fold the result. */
800 if (TREE_CODE (rhs) == MEM_REF
801 && TREE_OPERAND (rhs, 0) == name)
803 tree def_rhs_base;
804 poly_int64 def_rhs_offset;
805 if ((def_rhs_base = get_addr_base_and_unit_offset (TREE_OPERAND (def_rhs, 0),
806 &def_rhs_offset)))
808 poly_offset_int off = mem_ref_offset (rhs);
809 tree new_ptr;
810 off += def_rhs_offset;
811 if (TREE_CODE (def_rhs_base) == MEM_REF)
813 off += mem_ref_offset (def_rhs_base);
814 new_ptr = TREE_OPERAND (def_rhs_base, 0);
816 else
817 new_ptr = build_fold_addr_expr (def_rhs_base);
818 TREE_OPERAND (rhs, 0) = new_ptr;
819 TREE_OPERAND (rhs, 1)
820 = wide_int_to_tree (TREE_TYPE (TREE_OPERAND (rhs, 1)), off);
821 fold_stmt_inplace (use_stmt_gsi);
822 tidy_after_forward_propagate_addr (use_stmt);
823 return res;
825 /* If the RHS is a plain dereference and the value type is the same as
826 that of the pointed-to type of the address we can put the
827 dereferenced address on the RHS preserving the original alias-type. */
828 else if (integer_zerop (TREE_OPERAND (rhs, 1))
829 && ((gimple_assign_rhs1 (use_stmt) == rhs
830 && useless_type_conversion_p
831 (TREE_TYPE (gimple_assign_lhs (use_stmt)),
832 TREE_TYPE (TREE_OPERAND (def_rhs, 0))))
833 || types_compatible_p (TREE_TYPE (rhs),
834 TREE_TYPE (TREE_OPERAND (def_rhs, 0)))))
836 tree *def_rhs_basep = &TREE_OPERAND (def_rhs, 0);
837 tree new_offset, new_base, saved, new_rhs;
838 while (handled_component_p (*def_rhs_basep))
839 def_rhs_basep = &TREE_OPERAND (*def_rhs_basep, 0);
840 saved = *def_rhs_basep;
841 if (TREE_CODE (*def_rhs_basep) == MEM_REF)
843 new_base = TREE_OPERAND (*def_rhs_basep, 0);
844 new_offset = fold_convert (TREE_TYPE (TREE_OPERAND (rhs, 1)),
845 TREE_OPERAND (*def_rhs_basep, 1));
847 else
849 new_base = build_fold_addr_expr (*def_rhs_basep);
850 new_offset = TREE_OPERAND (rhs, 1);
852 *def_rhs_basep = build2 (MEM_REF, TREE_TYPE (*def_rhs_basep),
853 new_base, new_offset);
854 TREE_THIS_VOLATILE (*def_rhs_basep) = TREE_THIS_VOLATILE (rhs);
855 TREE_SIDE_EFFECTS (*def_rhs_basep) = TREE_SIDE_EFFECTS (rhs);
856 TREE_THIS_NOTRAP (*def_rhs_basep) = TREE_THIS_NOTRAP (rhs);
857 new_rhs = unshare_expr (TREE_OPERAND (def_rhs, 0));
858 *rhsp = new_rhs;
859 TREE_THIS_VOLATILE (new_rhs) = TREE_THIS_VOLATILE (rhs);
860 TREE_SIDE_EFFECTS (new_rhs) = TREE_SIDE_EFFECTS (rhs);
861 *def_rhs_basep = saved;
862 fold_stmt_inplace (use_stmt_gsi);
863 tidy_after_forward_propagate_addr (use_stmt);
864 return res;
868 /* If the use of the ADDR_EXPR is not a POINTER_PLUS_EXPR, there
869 is nothing to do. */
870 if (gimple_assign_rhs_code (use_stmt) != POINTER_PLUS_EXPR
871 || gimple_assign_rhs1 (use_stmt) != name)
872 return false;
874 /* The remaining cases are all for turning pointer arithmetic into
875 array indexing. They only apply when we have the address of
876 element zero in an array. If that is not the case then there
877 is nothing to do. */
878 array_ref = TREE_OPERAND (def_rhs, 0);
879 if ((TREE_CODE (array_ref) != ARRAY_REF
880 || TREE_CODE (TREE_TYPE (TREE_OPERAND (array_ref, 0))) != ARRAY_TYPE
881 || TREE_CODE (TREE_OPERAND (array_ref, 1)) != INTEGER_CST)
882 && TREE_CODE (TREE_TYPE (array_ref)) != ARRAY_TYPE)
883 return false;
885 rhs2 = gimple_assign_rhs2 (use_stmt);
886 /* Optimize &x[C1] p+ C2 to &x p+ C3 with C3 = C1 * element_size + C2. */
887 if (TREE_CODE (rhs2) == INTEGER_CST)
889 tree new_rhs = build1_loc (gimple_location (use_stmt),
890 ADDR_EXPR, TREE_TYPE (def_rhs),
891 fold_build2 (MEM_REF,
892 TREE_TYPE (TREE_TYPE (def_rhs)),
893 unshare_expr (def_rhs),
894 fold_convert (ptr_type_node,
895 rhs2)));
896 gimple_assign_set_rhs_from_tree (use_stmt_gsi, new_rhs);
897 use_stmt = gsi_stmt (*use_stmt_gsi);
898 update_stmt (use_stmt);
899 tidy_after_forward_propagate_addr (use_stmt);
900 return true;
903 return false;
906 /* STMT is a statement of the form SSA_NAME = ADDR_EXPR <whatever>.
908 Try to forward propagate the ADDR_EXPR into all uses of the SSA_NAME.
909 Often this will allow for removal of an ADDR_EXPR and INDIRECT_REF
910 node or for recovery of array indexing from pointer arithmetic.
912 PARENT_SINGLE_USE_P tells if, when in a recursive invocation, NAME was
913 the single use in the previous invocation. Pass true when calling
914 this as toplevel.
916 Returns true, if all uses have been propagated into. */
918 static bool
919 forward_propagate_addr_expr (tree name, tree rhs, bool parent_single_use_p)
921 imm_use_iterator iter;
922 gimple *use_stmt;
923 bool all = true;
924 bool single_use_p = parent_single_use_p && has_single_use (name);
926 FOR_EACH_IMM_USE_STMT (use_stmt, iter, name)
928 bool result;
929 tree use_rhs;
931 /* If the use is not in a simple assignment statement, then
932 there is nothing we can do. */
933 if (!is_gimple_assign (use_stmt))
935 if (!is_gimple_debug (use_stmt))
936 all = false;
937 continue;
940 gimple_stmt_iterator gsi = gsi_for_stmt (use_stmt);
941 result = forward_propagate_addr_expr_1 (name, rhs, &gsi,
942 single_use_p);
943 /* If the use has moved to a different statement adjust
944 the update machinery for the old statement too. */
945 if (use_stmt != gsi_stmt (gsi))
947 update_stmt (use_stmt);
948 use_stmt = gsi_stmt (gsi);
950 update_stmt (use_stmt);
951 all &= result;
953 /* Remove intermediate now unused copy and conversion chains. */
954 use_rhs = gimple_assign_rhs1 (use_stmt);
955 if (result
956 && TREE_CODE (gimple_assign_lhs (use_stmt)) == SSA_NAME
957 && TREE_CODE (use_rhs) == SSA_NAME
958 && has_zero_uses (gimple_assign_lhs (use_stmt)))
960 gimple_stmt_iterator gsi = gsi_for_stmt (use_stmt);
961 fwprop_invalidate_lattice (gimple_get_lhs (use_stmt));
962 release_defs (use_stmt);
963 gsi_remove (&gsi, true);
967 return all && has_zero_uses (name);
971 /* Helper function for simplify_gimple_switch. Remove case labels that
972 have values outside the range of the new type. */
974 static void
975 simplify_gimple_switch_label_vec (gswitch *stmt, tree index_type,
976 vec<std::pair<int, int> > &edges_to_remove)
978 unsigned int branch_num = gimple_switch_num_labels (stmt);
979 auto_vec<tree> labels (branch_num);
980 unsigned int i, len;
982 /* Collect the existing case labels in a VEC, and preprocess it as if
983 we are gimplifying a GENERIC SWITCH_EXPR. */
984 for (i = 1; i < branch_num; i++)
985 labels.quick_push (gimple_switch_label (stmt, i));
986 preprocess_case_label_vec_for_gimple (labels, index_type, NULL);
988 /* If any labels were removed, replace the existing case labels
989 in the GIMPLE_SWITCH statement with the correct ones.
990 Note that the type updates were done in-place on the case labels,
991 so we only have to replace the case labels in the GIMPLE_SWITCH
992 if the number of labels changed. */
993 len = labels.length ();
994 if (len < branch_num - 1)
996 bitmap target_blocks;
997 edge_iterator ei;
998 edge e;
1000 /* Corner case: *all* case labels have been removed as being
1001 out-of-range for INDEX_TYPE. Push one label and let the
1002 CFG cleanups deal with this further. */
1003 if (len == 0)
1005 tree label, elt;
1007 label = CASE_LABEL (gimple_switch_default_label (stmt));
1008 elt = build_case_label (build_int_cst (index_type, 0), NULL, label);
1009 labels.quick_push (elt);
1010 len = 1;
1013 for (i = 0; i < labels.length (); i++)
1014 gimple_switch_set_label (stmt, i + 1, labels[i]);
1015 for (i++ ; i < branch_num; i++)
1016 gimple_switch_set_label (stmt, i, NULL_TREE);
1017 gimple_switch_set_num_labels (stmt, len + 1);
1019 /* Cleanup any edges that are now dead. */
1020 target_blocks = BITMAP_ALLOC (NULL);
1021 for (i = 0; i < gimple_switch_num_labels (stmt); i++)
1023 tree elt = gimple_switch_label (stmt, i);
1024 basic_block target = label_to_block (cfun, CASE_LABEL (elt));
1025 bitmap_set_bit (target_blocks, target->index);
1027 for (ei = ei_start (gimple_bb (stmt)->succs); (e = ei_safe_edge (ei)); )
1029 if (! bitmap_bit_p (target_blocks, e->dest->index))
1030 edges_to_remove.safe_push (std::make_pair (e->src->index,
1031 e->dest->index));
1032 else
1033 ei_next (&ei);
1035 BITMAP_FREE (target_blocks);
1039 /* STMT is a SWITCH_EXPR for which we attempt to find equivalent forms of
1040 the condition which we may be able to optimize better. */
1042 static bool
1043 simplify_gimple_switch (gswitch *stmt,
1044 vec<std::pair<int, int> > &edges_to_remove)
1046 /* The optimization that we really care about is removing unnecessary
1047 casts. That will let us do much better in propagating the inferred
1048 constant at the switch target. */
1049 tree cond = gimple_switch_index (stmt);
1050 if (TREE_CODE (cond) == SSA_NAME)
1052 gimple *def_stmt = SSA_NAME_DEF_STMT (cond);
1053 if (gimple_assign_cast_p (def_stmt))
1055 tree def = gimple_assign_rhs1 (def_stmt);
1056 if (TREE_CODE (def) != SSA_NAME)
1057 return false;
1059 /* If we have an extension or sign-change that preserves the
1060 values we check against then we can copy the source value into
1061 the switch. */
1062 tree ti = TREE_TYPE (def);
1063 if (INTEGRAL_TYPE_P (ti)
1064 && TYPE_PRECISION (ti) <= TYPE_PRECISION (TREE_TYPE (cond)))
1066 size_t n = gimple_switch_num_labels (stmt);
1067 tree min = NULL_TREE, max = NULL_TREE;
1068 if (n > 1)
1070 min = CASE_LOW (gimple_switch_label (stmt, 1));
1071 if (CASE_HIGH (gimple_switch_label (stmt, n - 1)))
1072 max = CASE_HIGH (gimple_switch_label (stmt, n - 1));
1073 else
1074 max = CASE_LOW (gimple_switch_label (stmt, n - 1));
1076 if ((!min || int_fits_type_p (min, ti))
1077 && (!max || int_fits_type_p (max, ti)))
1079 gimple_switch_set_index (stmt, def);
1080 simplify_gimple_switch_label_vec (stmt, ti,
1081 edges_to_remove);
1082 update_stmt (stmt);
1083 return true;
1089 return false;
1092 /* For pointers p2 and p1 return p2 - p1 if the
1093 difference is known and constant, otherwise return NULL. */
1095 static tree
1096 constant_pointer_difference (tree p1, tree p2)
1098 int i, j;
1099 #define CPD_ITERATIONS 5
1100 tree exps[2][CPD_ITERATIONS];
1101 tree offs[2][CPD_ITERATIONS];
1102 int cnt[2];
1104 for (i = 0; i < 2; i++)
1106 tree p = i ? p1 : p2;
1107 tree off = size_zero_node;
1108 gimple *stmt;
1109 enum tree_code code;
1111 /* For each of p1 and p2 we need to iterate at least
1112 twice, to handle ADDR_EXPR directly in p1/p2,
1113 SSA_NAME with ADDR_EXPR or POINTER_PLUS_EXPR etc.
1114 on definition's stmt RHS. Iterate a few extra times. */
1115 j = 0;
1118 if (!POINTER_TYPE_P (TREE_TYPE (p)))
1119 break;
1120 if (TREE_CODE (p) == ADDR_EXPR)
1122 tree q = TREE_OPERAND (p, 0);
1123 poly_int64 offset;
1124 tree base = get_addr_base_and_unit_offset (q, &offset);
1125 if (base)
1127 q = base;
1128 if (maybe_ne (offset, 0))
1129 off = size_binop (PLUS_EXPR, off, size_int (offset));
1131 if (TREE_CODE (q) == MEM_REF
1132 && TREE_CODE (TREE_OPERAND (q, 0)) == SSA_NAME)
1134 p = TREE_OPERAND (q, 0);
1135 off = size_binop (PLUS_EXPR, off,
1136 wide_int_to_tree (sizetype,
1137 mem_ref_offset (q)));
1139 else
1141 exps[i][j] = q;
1142 offs[i][j++] = off;
1143 break;
1146 if (TREE_CODE (p) != SSA_NAME)
1147 break;
1148 exps[i][j] = p;
1149 offs[i][j++] = off;
1150 if (j == CPD_ITERATIONS)
1151 break;
1152 stmt = SSA_NAME_DEF_STMT (p);
1153 if (!is_gimple_assign (stmt) || gimple_assign_lhs (stmt) != p)
1154 break;
1155 code = gimple_assign_rhs_code (stmt);
1156 if (code == POINTER_PLUS_EXPR)
1158 if (TREE_CODE (gimple_assign_rhs2 (stmt)) != INTEGER_CST)
1159 break;
1160 off = size_binop (PLUS_EXPR, off, gimple_assign_rhs2 (stmt));
1161 p = gimple_assign_rhs1 (stmt);
1163 else if (code == ADDR_EXPR || CONVERT_EXPR_CODE_P (code))
1164 p = gimple_assign_rhs1 (stmt);
1165 else
1166 break;
1168 while (1);
1169 cnt[i] = j;
1172 for (i = 0; i < cnt[0]; i++)
1173 for (j = 0; j < cnt[1]; j++)
1174 if (exps[0][i] == exps[1][j])
1175 return size_binop (MINUS_EXPR, offs[0][i], offs[1][j]);
1177 return NULL_TREE;
1180 /* *GSI_P is a GIMPLE_CALL to a builtin function.
1181 Optimize
1182 memcpy (p, "abcd", 4);
1183 memset (p + 4, ' ', 3);
1184 into
1185 memcpy (p, "abcd ", 7);
1186 call if the latter can be stored by pieces during expansion.
1188 Optimize
1189 memchr ("abcd", a, 4) == 0;
1191 memchr ("abcd", a, 4) != 0;
1193 (a == 'a' || a == 'b' || a == 'c' || a == 'd') == 0
1195 (a == 'a' || a == 'b' || a == 'c' || a == 'd') != 0
1197 Also canonicalize __atomic_fetch_op (p, x, y) op x
1198 to __atomic_op_fetch (p, x, y) or
1199 __atomic_op_fetch (p, x, y) iop x
1200 to __atomic_fetch_op (p, x, y) when possible (also __sync). */
1202 static bool
1203 simplify_builtin_call (gimple_stmt_iterator *gsi_p, tree callee2)
1205 gimple *stmt1, *stmt2 = gsi_stmt (*gsi_p);
1206 enum built_in_function other_atomic = END_BUILTINS;
1207 enum tree_code atomic_op = ERROR_MARK;
1208 tree vuse = gimple_vuse (stmt2);
1209 if (vuse == NULL)
1210 return false;
1211 stmt1 = SSA_NAME_DEF_STMT (vuse);
1213 tree res;
1215 switch (DECL_FUNCTION_CODE (callee2))
1217 case BUILT_IN_MEMCHR:
1218 if (gimple_call_num_args (stmt2) == 3
1219 && (res = gimple_call_lhs (stmt2)) != nullptr
1220 && use_in_zero_equality (res) != nullptr
1221 && CHAR_BIT == 8
1222 && BITS_PER_UNIT == 8)
1224 tree ptr = gimple_call_arg (stmt2, 0);
1225 if (TREE_CODE (ptr) != ADDR_EXPR
1226 || TREE_CODE (TREE_OPERAND (ptr, 0)) != STRING_CST)
1227 break;
1228 unsigned HOST_WIDE_INT slen
1229 = TREE_STRING_LENGTH (TREE_OPERAND (ptr, 0));
1230 /* It must be a non-empty string constant. */
1231 if (slen < 2)
1232 break;
1233 /* For -Os, only simplify strings with a single character. */
1234 if (!optimize_bb_for_speed_p (gimple_bb (stmt2))
1235 && slen > 2)
1236 break;
1237 tree size = gimple_call_arg (stmt2, 2);
1238 /* Size must be a constant which is <= UNITS_PER_WORD and
1239 <= the string length. */
1240 if (TREE_CODE (size) != INTEGER_CST)
1241 break;
1243 if (!tree_fits_uhwi_p (size))
1244 break;
1246 unsigned HOST_WIDE_INT sz = tree_to_uhwi (size);
1247 if (sz == 0 || sz > UNITS_PER_WORD || sz >= slen)
1248 break;
1250 tree ch = gimple_call_arg (stmt2, 1);
1251 location_t loc = gimple_location (stmt2);
1252 if (!useless_type_conversion_p (char_type_node,
1253 TREE_TYPE (ch)))
1254 ch = fold_convert_loc (loc, char_type_node, ch);
1255 const char *p = TREE_STRING_POINTER (TREE_OPERAND (ptr, 0));
1256 unsigned int isize = sz;
1257 tree *op = XALLOCAVEC (tree, isize);
1258 for (unsigned int i = 0; i < isize; i++)
1260 op[i] = build_int_cst (char_type_node, p[i]);
1261 op[i] = fold_build2_loc (loc, EQ_EXPR, boolean_type_node,
1262 op[i], ch);
1264 for (unsigned int i = isize - 1; i >= 1; i--)
1265 op[i - 1] = fold_convert_loc (loc, boolean_type_node,
1266 fold_build2_loc (loc,
1267 BIT_IOR_EXPR,
1268 boolean_type_node,
1269 op[i - 1],
1270 op[i]));
1271 res = fold_convert_loc (loc, TREE_TYPE (res), op[0]);
1272 gimplify_and_update_call_from_tree (gsi_p, res);
1273 return true;
1275 break;
1277 case BUILT_IN_MEMSET:
1278 if (gimple_call_num_args (stmt2) != 3
1279 || gimple_call_lhs (stmt2)
1280 || CHAR_BIT != 8
1281 || BITS_PER_UNIT != 8)
1282 break;
1283 else
1285 tree callee1;
1286 tree ptr1, src1, str1, off1, len1, lhs1;
1287 tree ptr2 = gimple_call_arg (stmt2, 0);
1288 tree val2 = gimple_call_arg (stmt2, 1);
1289 tree len2 = gimple_call_arg (stmt2, 2);
1290 tree diff, vdef, new_str_cst;
1291 gimple *use_stmt;
1292 unsigned int ptr1_align;
1293 unsigned HOST_WIDE_INT src_len;
1294 char *src_buf;
1295 use_operand_p use_p;
1297 if (!tree_fits_shwi_p (val2)
1298 || !tree_fits_uhwi_p (len2)
1299 || compare_tree_int (len2, 1024) == 1)
1300 break;
1301 if (is_gimple_call (stmt1))
1303 /* If first stmt is a call, it needs to be memcpy
1304 or mempcpy, with string literal as second argument and
1305 constant length. */
1306 callee1 = gimple_call_fndecl (stmt1);
1307 if (callee1 == NULL_TREE
1308 || !fndecl_built_in_p (callee1, BUILT_IN_NORMAL)
1309 || gimple_call_num_args (stmt1) != 3)
1310 break;
1311 if (DECL_FUNCTION_CODE (callee1) != BUILT_IN_MEMCPY
1312 && DECL_FUNCTION_CODE (callee1) != BUILT_IN_MEMPCPY)
1313 break;
1314 ptr1 = gimple_call_arg (stmt1, 0);
1315 src1 = gimple_call_arg (stmt1, 1);
1316 len1 = gimple_call_arg (stmt1, 2);
1317 lhs1 = gimple_call_lhs (stmt1);
1318 if (!tree_fits_uhwi_p (len1))
1319 break;
1320 str1 = string_constant (src1, &off1, NULL, NULL);
1321 if (str1 == NULL_TREE)
1322 break;
1323 if (!tree_fits_uhwi_p (off1)
1324 || compare_tree_int (off1, TREE_STRING_LENGTH (str1) - 1) > 0
1325 || compare_tree_int (len1, TREE_STRING_LENGTH (str1)
1326 - tree_to_uhwi (off1)) > 0
1327 || TREE_CODE (TREE_TYPE (str1)) != ARRAY_TYPE
1328 || TYPE_MODE (TREE_TYPE (TREE_TYPE (str1)))
1329 != TYPE_MODE (char_type_node))
1330 break;
1332 else if (gimple_assign_single_p (stmt1))
1334 /* Otherwise look for length 1 memcpy optimized into
1335 assignment. */
1336 ptr1 = gimple_assign_lhs (stmt1);
1337 src1 = gimple_assign_rhs1 (stmt1);
1338 if (TREE_CODE (ptr1) != MEM_REF
1339 || TYPE_MODE (TREE_TYPE (ptr1)) != TYPE_MODE (char_type_node)
1340 || !tree_fits_shwi_p (src1))
1341 break;
1342 ptr1 = build_fold_addr_expr (ptr1);
1343 STRIP_USELESS_TYPE_CONVERSION (ptr1);
1344 callee1 = NULL_TREE;
1345 len1 = size_one_node;
1346 lhs1 = NULL_TREE;
1347 off1 = size_zero_node;
1348 str1 = NULL_TREE;
1350 else
1351 break;
1353 diff = constant_pointer_difference (ptr1, ptr2);
1354 if (diff == NULL && lhs1 != NULL)
1356 diff = constant_pointer_difference (lhs1, ptr2);
1357 if (DECL_FUNCTION_CODE (callee1) == BUILT_IN_MEMPCPY
1358 && diff != NULL)
1359 diff = size_binop (PLUS_EXPR, diff,
1360 fold_convert (sizetype, len1));
1362 /* If the difference between the second and first destination pointer
1363 is not constant, or is bigger than memcpy length, bail out. */
1364 if (diff == NULL
1365 || !tree_fits_uhwi_p (diff)
1366 || tree_int_cst_lt (len1, diff)
1367 || compare_tree_int (diff, 1024) == 1)
1368 break;
1370 /* Use maximum of difference plus memset length and memcpy length
1371 as the new memcpy length, if it is too big, bail out. */
1372 src_len = tree_to_uhwi (diff);
1373 src_len += tree_to_uhwi (len2);
1374 if (src_len < tree_to_uhwi (len1))
1375 src_len = tree_to_uhwi (len1);
1376 if (src_len > 1024)
1377 break;
1379 /* If mempcpy value is used elsewhere, bail out, as mempcpy
1380 with bigger length will return different result. */
1381 if (lhs1 != NULL_TREE
1382 && DECL_FUNCTION_CODE (callee1) == BUILT_IN_MEMPCPY
1383 && (TREE_CODE (lhs1) != SSA_NAME
1384 || !single_imm_use (lhs1, &use_p, &use_stmt)
1385 || use_stmt != stmt2))
1386 break;
1388 /* If anything reads memory in between memcpy and memset
1389 call, the modified memcpy call might change it. */
1390 vdef = gimple_vdef (stmt1);
1391 if (vdef != NULL
1392 && (!single_imm_use (vdef, &use_p, &use_stmt)
1393 || use_stmt != stmt2))
1394 break;
1396 ptr1_align = get_pointer_alignment (ptr1);
1397 /* Construct the new source string literal. */
1398 src_buf = XALLOCAVEC (char, src_len + 1);
1399 if (callee1)
1400 memcpy (src_buf,
1401 TREE_STRING_POINTER (str1) + tree_to_uhwi (off1),
1402 tree_to_uhwi (len1));
1403 else
1404 src_buf[0] = tree_to_shwi (src1);
1405 memset (src_buf + tree_to_uhwi (diff),
1406 tree_to_shwi (val2), tree_to_uhwi (len2));
1407 src_buf[src_len] = '\0';
1408 /* Neither builtin_strncpy_read_str nor builtin_memcpy_read_str
1409 handle embedded '\0's. */
1410 if (strlen (src_buf) != src_len)
1411 break;
1412 rtl_profile_for_bb (gimple_bb (stmt2));
1413 /* If the new memcpy wouldn't be emitted by storing the literal
1414 by pieces, this optimization might enlarge .rodata too much,
1415 as commonly used string literals couldn't be shared any
1416 longer. */
1417 if (!can_store_by_pieces (src_len,
1418 builtin_strncpy_read_str,
1419 src_buf, ptr1_align, false))
1420 break;
1422 new_str_cst = build_string_literal (src_len, src_buf);
1423 if (callee1)
1425 /* If STMT1 is a mem{,p}cpy call, adjust it and remove
1426 memset call. */
1427 if (lhs1 && DECL_FUNCTION_CODE (callee1) == BUILT_IN_MEMPCPY)
1428 gimple_call_set_lhs (stmt1, NULL_TREE);
1429 gimple_call_set_arg (stmt1, 1, new_str_cst);
1430 gimple_call_set_arg (stmt1, 2,
1431 build_int_cst (TREE_TYPE (len1), src_len));
1432 update_stmt (stmt1);
1433 unlink_stmt_vdef (stmt2);
1434 gsi_replace (gsi_p, gimple_build_nop (), false);
1435 fwprop_invalidate_lattice (gimple_get_lhs (stmt2));
1436 release_defs (stmt2);
1437 if (lhs1 && DECL_FUNCTION_CODE (callee1) == BUILT_IN_MEMPCPY)
1439 fwprop_invalidate_lattice (lhs1);
1440 release_ssa_name (lhs1);
1442 return true;
1444 else
1446 /* Otherwise, if STMT1 is length 1 memcpy optimized into
1447 assignment, remove STMT1 and change memset call into
1448 memcpy call. */
1449 gimple_stmt_iterator gsi = gsi_for_stmt (stmt1);
1451 if (!is_gimple_val (ptr1))
1452 ptr1 = force_gimple_operand_gsi (gsi_p, ptr1, true, NULL_TREE,
1453 true, GSI_SAME_STMT);
1454 tree fndecl = builtin_decl_explicit (BUILT_IN_MEMCPY);
1455 gimple_call_set_fndecl (stmt2, fndecl);
1456 gimple_call_set_fntype (as_a <gcall *> (stmt2),
1457 TREE_TYPE (fndecl));
1458 gimple_call_set_arg (stmt2, 0, ptr1);
1459 gimple_call_set_arg (stmt2, 1, new_str_cst);
1460 gimple_call_set_arg (stmt2, 2,
1461 build_int_cst (TREE_TYPE (len2), src_len));
1462 unlink_stmt_vdef (stmt1);
1463 gsi_remove (&gsi, true);
1464 fwprop_invalidate_lattice (gimple_get_lhs (stmt1));
1465 release_defs (stmt1);
1466 update_stmt (stmt2);
1467 return false;
1470 break;
1472 #define CASE_ATOMIC(NAME, OTHER, OP) \
1473 case BUILT_IN_##NAME##_1: \
1474 case BUILT_IN_##NAME##_2: \
1475 case BUILT_IN_##NAME##_4: \
1476 case BUILT_IN_##NAME##_8: \
1477 case BUILT_IN_##NAME##_16: \
1478 atomic_op = OP; \
1479 other_atomic \
1480 = (enum built_in_function) (BUILT_IN_##OTHER##_1 \
1481 + (DECL_FUNCTION_CODE (callee2) \
1482 - BUILT_IN_##NAME##_1)); \
1483 goto handle_atomic_fetch_op;
1485 CASE_ATOMIC (ATOMIC_FETCH_ADD, ATOMIC_ADD_FETCH, PLUS_EXPR)
1486 CASE_ATOMIC (ATOMIC_FETCH_SUB, ATOMIC_SUB_FETCH, MINUS_EXPR)
1487 CASE_ATOMIC (ATOMIC_FETCH_AND, ATOMIC_AND_FETCH, BIT_AND_EXPR)
1488 CASE_ATOMIC (ATOMIC_FETCH_XOR, ATOMIC_XOR_FETCH, BIT_XOR_EXPR)
1489 CASE_ATOMIC (ATOMIC_FETCH_OR, ATOMIC_OR_FETCH, BIT_IOR_EXPR)
1491 CASE_ATOMIC (SYNC_FETCH_AND_ADD, SYNC_ADD_AND_FETCH, PLUS_EXPR)
1492 CASE_ATOMIC (SYNC_FETCH_AND_SUB, SYNC_SUB_AND_FETCH, MINUS_EXPR)
1493 CASE_ATOMIC (SYNC_FETCH_AND_AND, SYNC_AND_AND_FETCH, BIT_AND_EXPR)
1494 CASE_ATOMIC (SYNC_FETCH_AND_XOR, SYNC_XOR_AND_FETCH, BIT_XOR_EXPR)
1495 CASE_ATOMIC (SYNC_FETCH_AND_OR, SYNC_OR_AND_FETCH, BIT_IOR_EXPR)
1497 CASE_ATOMIC (ATOMIC_ADD_FETCH, ATOMIC_FETCH_ADD, MINUS_EXPR)
1498 CASE_ATOMIC (ATOMIC_SUB_FETCH, ATOMIC_FETCH_SUB, PLUS_EXPR)
1499 CASE_ATOMIC (ATOMIC_XOR_FETCH, ATOMIC_FETCH_XOR, BIT_XOR_EXPR)
1501 CASE_ATOMIC (SYNC_ADD_AND_FETCH, SYNC_FETCH_AND_ADD, MINUS_EXPR)
1502 CASE_ATOMIC (SYNC_SUB_AND_FETCH, SYNC_FETCH_AND_SUB, PLUS_EXPR)
1503 CASE_ATOMIC (SYNC_XOR_AND_FETCH, SYNC_FETCH_AND_XOR, BIT_XOR_EXPR)
1505 #undef CASE_ATOMIC
1507 handle_atomic_fetch_op:
1508 if (gimple_call_num_args (stmt2) >= 2 && gimple_call_lhs (stmt2))
1510 tree lhs2 = gimple_call_lhs (stmt2), lhsc = lhs2;
1511 tree arg = gimple_call_arg (stmt2, 1);
1512 gimple *use_stmt, *cast_stmt = NULL;
1513 use_operand_p use_p;
1514 tree ndecl = builtin_decl_explicit (other_atomic);
1516 if (ndecl == NULL_TREE || !single_imm_use (lhs2, &use_p, &use_stmt))
1517 break;
1519 if (gimple_assign_cast_p (use_stmt))
1521 cast_stmt = use_stmt;
1522 lhsc = gimple_assign_lhs (cast_stmt);
1523 if (lhsc == NULL_TREE
1524 || !INTEGRAL_TYPE_P (TREE_TYPE (lhsc))
1525 || (TYPE_PRECISION (TREE_TYPE (lhsc))
1526 != TYPE_PRECISION (TREE_TYPE (lhs2)))
1527 || !single_imm_use (lhsc, &use_p, &use_stmt))
1529 use_stmt = cast_stmt;
1530 cast_stmt = NULL;
1531 lhsc = lhs2;
1535 bool ok = false;
1536 tree oarg = NULL_TREE;
1537 enum tree_code ccode = ERROR_MARK;
1538 tree crhs1 = NULL_TREE, crhs2 = NULL_TREE;
1539 if (is_gimple_assign (use_stmt)
1540 && gimple_assign_rhs_code (use_stmt) == atomic_op)
1542 if (gimple_assign_rhs1 (use_stmt) == lhsc)
1543 oarg = gimple_assign_rhs2 (use_stmt);
1544 else if (atomic_op != MINUS_EXPR)
1545 oarg = gimple_assign_rhs1 (use_stmt);
1547 else if (atomic_op == MINUS_EXPR
1548 && is_gimple_assign (use_stmt)
1549 && gimple_assign_rhs_code (use_stmt) == PLUS_EXPR
1550 && TREE_CODE (arg) == INTEGER_CST
1551 && (TREE_CODE (gimple_assign_rhs2 (use_stmt))
1552 == INTEGER_CST))
1554 tree a = fold_convert (TREE_TYPE (lhs2), arg);
1555 tree o = fold_convert (TREE_TYPE (lhs2),
1556 gimple_assign_rhs2 (use_stmt));
1557 if (wi::to_wide (a) == wi::neg (wi::to_wide (o)))
1558 ok = true;
1560 else if (atomic_op == BIT_AND_EXPR || atomic_op == BIT_IOR_EXPR)
1562 else if (gimple_code (use_stmt) == GIMPLE_COND)
1564 ccode = gimple_cond_code (use_stmt);
1565 crhs1 = gimple_cond_lhs (use_stmt);
1566 crhs2 = gimple_cond_rhs (use_stmt);
1568 else if (is_gimple_assign (use_stmt))
1570 if (gimple_assign_rhs_class (use_stmt) == GIMPLE_BINARY_RHS)
1572 ccode = gimple_assign_rhs_code (use_stmt);
1573 crhs1 = gimple_assign_rhs1 (use_stmt);
1574 crhs2 = gimple_assign_rhs2 (use_stmt);
1576 else if (gimple_assign_rhs_code (use_stmt) == COND_EXPR)
1578 tree cond = gimple_assign_rhs1 (use_stmt);
1579 if (COMPARISON_CLASS_P (cond))
1581 ccode = TREE_CODE (cond);
1582 crhs1 = TREE_OPERAND (cond, 0);
1583 crhs2 = TREE_OPERAND (cond, 1);
1587 if (ccode == EQ_EXPR || ccode == NE_EXPR)
1589 /* Deal with x - y == 0 or x ^ y == 0
1590 being optimized into x == y and x + cst == 0
1591 into x == -cst. */
1592 tree o = NULL_TREE;
1593 if (crhs1 == lhsc)
1594 o = crhs2;
1595 else if (crhs2 == lhsc)
1596 o = crhs1;
1597 if (o && atomic_op != PLUS_EXPR)
1598 oarg = o;
1599 else if (o
1600 && TREE_CODE (o) == INTEGER_CST
1601 && TREE_CODE (arg) == INTEGER_CST)
1603 tree a = fold_convert (TREE_TYPE (lhs2), arg);
1604 o = fold_convert (TREE_TYPE (lhs2), o);
1605 if (wi::to_wide (a) == wi::neg (wi::to_wide (o)))
1606 ok = true;
1609 if (oarg && !ok)
1611 if (operand_equal_p (arg, oarg, 0))
1612 ok = true;
1613 else if (TREE_CODE (arg) == SSA_NAME
1614 && TREE_CODE (oarg) == SSA_NAME)
1616 tree oarg2 = oarg;
1617 if (gimple_assign_cast_p (SSA_NAME_DEF_STMT (oarg)))
1619 gimple *g = SSA_NAME_DEF_STMT (oarg);
1620 oarg2 = gimple_assign_rhs1 (g);
1621 if (TREE_CODE (oarg2) != SSA_NAME
1622 || !INTEGRAL_TYPE_P (TREE_TYPE (oarg2))
1623 || (TYPE_PRECISION (TREE_TYPE (oarg2))
1624 != TYPE_PRECISION (TREE_TYPE (oarg))))
1625 oarg2 = oarg;
1627 if (gimple_assign_cast_p (SSA_NAME_DEF_STMT (arg)))
1629 gimple *g = SSA_NAME_DEF_STMT (arg);
1630 tree rhs1 = gimple_assign_rhs1 (g);
1631 /* Handle e.g.
1632 x.0_1 = (long unsigned int) x_4(D);
1633 _2 = __atomic_fetch_add_8 (&vlong, x.0_1, 0);
1634 _3 = (long int) _2;
1635 _7 = x_4(D) + _3; */
1636 if (rhs1 == oarg || rhs1 == oarg2)
1637 ok = true;
1638 /* Handle e.g.
1639 x.18_1 = (short unsigned int) x_5(D);
1640 _2 = (int) x.18_1;
1641 _3 = __atomic_fetch_xor_2 (&vshort, _2, 0);
1642 _4 = (short int) _3;
1643 _8 = x_5(D) ^ _4;
1644 This happens only for char/short. */
1645 else if (TREE_CODE (rhs1) == SSA_NAME
1646 && INTEGRAL_TYPE_P (TREE_TYPE (rhs1))
1647 && (TYPE_PRECISION (TREE_TYPE (rhs1))
1648 == TYPE_PRECISION (TREE_TYPE (lhs2))))
1650 g = SSA_NAME_DEF_STMT (rhs1);
1651 if (gimple_assign_cast_p (g)
1652 && (gimple_assign_rhs1 (g) == oarg
1653 || gimple_assign_rhs1 (g) == oarg2))
1654 ok = true;
1657 if (!ok && arg == oarg2)
1658 /* Handle e.g.
1659 _1 = __sync_fetch_and_add_4 (&v, x_5(D));
1660 _2 = (int) _1;
1661 x.0_3 = (int) x_5(D);
1662 _7 = _2 + x.0_3; */
1663 ok = true;
1667 if (ok)
1669 tree new_lhs = make_ssa_name (TREE_TYPE (lhs2));
1670 gimple_call_set_lhs (stmt2, new_lhs);
1671 gimple_call_set_fndecl (stmt2, ndecl);
1672 gimple_stmt_iterator gsi = gsi_for_stmt (use_stmt);
1673 if (ccode == ERROR_MARK)
1674 gimple_assign_set_rhs_with_ops (&gsi, cast_stmt
1675 ? NOP_EXPR : SSA_NAME,
1676 new_lhs);
1677 else
1679 crhs1 = new_lhs;
1680 crhs2 = build_zero_cst (TREE_TYPE (lhs2));
1681 if (gimple_code (use_stmt) == GIMPLE_COND)
1683 gcond *cond_stmt = as_a <gcond *> (use_stmt);
1684 gimple_cond_set_lhs (cond_stmt, crhs1);
1685 gimple_cond_set_rhs (cond_stmt, crhs2);
1687 else if (gimple_assign_rhs_class (use_stmt)
1688 == GIMPLE_BINARY_RHS)
1690 gimple_assign_set_rhs1 (use_stmt, crhs1);
1691 gimple_assign_set_rhs2 (use_stmt, crhs2);
1693 else
1695 gcc_checking_assert (gimple_assign_rhs_code (use_stmt)
1696 == COND_EXPR);
1697 tree cond = build2 (ccode, boolean_type_node,
1698 crhs1, crhs2);
1699 gimple_assign_set_rhs1 (use_stmt, cond);
1702 update_stmt (use_stmt);
1703 if (atomic_op != BIT_AND_EXPR
1704 && atomic_op != BIT_IOR_EXPR
1705 && !stmt_ends_bb_p (stmt2))
1707 /* For the benefit of debug stmts, emit stmt(s) to set
1708 lhs2 to the value it had from the new builtin.
1709 E.g. if it was previously:
1710 lhs2 = __atomic_fetch_add_8 (ptr, arg, 0);
1711 emit:
1712 new_lhs = __atomic_add_fetch_8 (ptr, arg, 0);
1713 lhs2 = new_lhs - arg;
1714 We also keep cast_stmt if any in the IL for
1715 the same reasons.
1716 These stmts will be DCEd later and proper debug info
1717 will be emitted.
1718 This is only possible for reversible operations
1719 (+/-/^) and without -fnon-call-exceptions. */
1720 gsi = gsi_for_stmt (stmt2);
1721 tree type = TREE_TYPE (lhs2);
1722 if (TREE_CODE (arg) == INTEGER_CST)
1723 arg = fold_convert (type, arg);
1724 else if (!useless_type_conversion_p (type, TREE_TYPE (arg)))
1726 tree narg = make_ssa_name (type);
1727 gimple *g = gimple_build_assign (narg, NOP_EXPR, arg);
1728 gsi_insert_after (&gsi, g, GSI_NEW_STMT);
1729 arg = narg;
1731 enum tree_code rcode;
1732 switch (atomic_op)
1734 case PLUS_EXPR: rcode = MINUS_EXPR; break;
1735 case MINUS_EXPR: rcode = PLUS_EXPR; break;
1736 case BIT_XOR_EXPR: rcode = atomic_op; break;
1737 default: gcc_unreachable ();
1739 gimple *g = gimple_build_assign (lhs2, rcode, new_lhs, arg);
1740 gsi_insert_after (&gsi, g, GSI_NEW_STMT);
1741 update_stmt (stmt2);
1743 else
1745 /* For e.g.
1746 lhs2 = __atomic_fetch_or_8 (ptr, arg, 0);
1747 after we change it to
1748 new_lhs = __atomic_or_fetch_8 (ptr, arg, 0);
1749 there is no way to find out the lhs2 value (i.e.
1750 what the atomic memory contained before the operation),
1751 values of some bits are lost. We have checked earlier
1752 that we don't have any non-debug users except for what
1753 we are already changing, so we need to reset the
1754 debug stmts and remove the cast_stmt if any. */
1755 imm_use_iterator iter;
1756 FOR_EACH_IMM_USE_STMT (use_stmt, iter, lhs2)
1757 if (use_stmt != cast_stmt)
1759 gcc_assert (is_gimple_debug (use_stmt));
1760 gimple_debug_bind_reset_value (use_stmt);
1761 update_stmt (use_stmt);
1763 if (cast_stmt)
1765 gsi = gsi_for_stmt (cast_stmt);
1766 gsi_remove (&gsi, true);
1768 update_stmt (stmt2);
1769 release_ssa_name (lhs2);
1773 break;
1775 default:
1776 break;
1778 return false;
1781 /* Given a ssa_name in NAME see if it was defined by an assignment and
1782 set CODE to be the code and ARG1 to the first operand on the rhs and ARG2
1783 to the second operand on the rhs. */
1785 static inline void
1786 defcodefor_name (tree name, enum tree_code *code, tree *arg1, tree *arg2)
1788 gimple *def;
1789 enum tree_code code1;
1790 tree arg11;
1791 tree arg21;
1792 tree arg31;
1793 enum gimple_rhs_class grhs_class;
1795 code1 = TREE_CODE (name);
1796 arg11 = name;
1797 arg21 = NULL_TREE;
1798 arg31 = NULL_TREE;
1799 grhs_class = get_gimple_rhs_class (code1);
1801 if (code1 == SSA_NAME)
1803 def = SSA_NAME_DEF_STMT (name);
1805 if (def && is_gimple_assign (def)
1806 && can_propagate_from (def))
1808 code1 = gimple_assign_rhs_code (def);
1809 arg11 = gimple_assign_rhs1 (def);
1810 arg21 = gimple_assign_rhs2 (def);
1811 arg31 = gimple_assign_rhs3 (def);
1814 else if (grhs_class != GIMPLE_SINGLE_RHS)
1815 code1 = ERROR_MARK;
1817 *code = code1;
1818 *arg1 = arg11;
1819 if (arg2)
1820 *arg2 = arg21;
1821 if (arg31)
1822 *code = ERROR_MARK;
1826 /* Recognize rotation patterns. Return true if a transformation
1827 applied, otherwise return false.
1829 We are looking for X with unsigned type T with bitsize B, OP being
1830 +, | or ^, some type T2 wider than T. For:
1831 (X << CNT1) OP (X >> CNT2) iff CNT1 + CNT2 == B
1832 ((T) ((T2) X << CNT1)) OP ((T) ((T2) X >> CNT2)) iff CNT1 + CNT2 == B
1834 transform these into:
1835 X r<< CNT1
1837 Or for:
1838 (X << Y) OP (X >> (B - Y))
1839 (X << (int) Y) OP (X >> (int) (B - Y))
1840 ((T) ((T2) X << Y)) OP ((T) ((T2) X >> (B - Y)))
1841 ((T) ((T2) X << (int) Y)) OP ((T) ((T2) X >> (int) (B - Y)))
1842 (X << Y) | (X >> ((-Y) & (B - 1)))
1843 (X << (int) Y) | (X >> (int) ((-Y) & (B - 1)))
1844 ((T) ((T2) X << Y)) | ((T) ((T2) X >> ((-Y) & (B - 1))))
1845 ((T) ((T2) X << (int) Y)) | ((T) ((T2) X >> (int) ((-Y) & (B - 1))))
1847 transform these into (last 2 only if ranger can prove Y < B
1848 or Y = N * B):
1849 X r<< Y
1851 X r<< (& & (B - 1))
1852 The latter for the forms with T2 wider than T if ranger can't prove Y < B.
1854 Or for:
1855 (X << (Y & (B - 1))) | (X >> ((-Y) & (B - 1)))
1856 (X << (int) (Y & (B - 1))) | (X >> (int) ((-Y) & (B - 1)))
1857 ((T) ((T2) X << (Y & (B - 1)))) | ((T) ((T2) X >> ((-Y) & (B - 1))))
1858 ((T) ((T2) X << (int) (Y & (B - 1)))) \
1859 | ((T) ((T2) X >> (int) ((-Y) & (B - 1))))
1861 transform these into:
1862 X r<< (Y & (B - 1))
1864 Note, in the patterns with T2 type, the type of OP operands
1865 might be even a signed type, but should have precision B.
1866 Expressions with & (B - 1) should be recognized only if B is
1867 a power of 2. */
1869 static bool
1870 simplify_rotate (gimple_stmt_iterator *gsi)
1872 gimple *stmt = gsi_stmt (*gsi);
1873 tree arg[2], rtype, rotcnt = NULL_TREE;
1874 tree def_arg1[2], def_arg2[2];
1875 enum tree_code def_code[2];
1876 tree lhs;
1877 int i;
1878 bool swapped_p = false;
1879 gimple *g;
1880 gimple *def_arg_stmt[2] = { NULL, NULL };
1881 int wider_prec = 0;
1882 bool add_masking = false;
1884 arg[0] = gimple_assign_rhs1 (stmt);
1885 arg[1] = gimple_assign_rhs2 (stmt);
1886 rtype = TREE_TYPE (arg[0]);
1888 /* Only create rotates in complete modes. Other cases are not
1889 expanded properly. */
1890 if (!INTEGRAL_TYPE_P (rtype)
1891 || !type_has_mode_precision_p (rtype))
1892 return false;
1894 for (i = 0; i < 2; i++)
1896 defcodefor_name (arg[i], &def_code[i], &def_arg1[i], &def_arg2[i]);
1897 if (TREE_CODE (arg[i]) == SSA_NAME)
1898 def_arg_stmt[i] = SSA_NAME_DEF_STMT (arg[i]);
1901 /* Look through narrowing (or same precision) conversions. */
1902 if (CONVERT_EXPR_CODE_P (def_code[0])
1903 && CONVERT_EXPR_CODE_P (def_code[1])
1904 && INTEGRAL_TYPE_P (TREE_TYPE (def_arg1[0]))
1905 && INTEGRAL_TYPE_P (TREE_TYPE (def_arg1[1]))
1906 && TYPE_PRECISION (TREE_TYPE (def_arg1[0]))
1907 == TYPE_PRECISION (TREE_TYPE (def_arg1[1]))
1908 && TYPE_PRECISION (TREE_TYPE (def_arg1[0])) >= TYPE_PRECISION (rtype)
1909 && has_single_use (arg[0])
1910 && has_single_use (arg[1]))
1912 wider_prec = TYPE_PRECISION (TREE_TYPE (def_arg1[0]));
1913 for (i = 0; i < 2; i++)
1915 arg[i] = def_arg1[i];
1916 defcodefor_name (arg[i], &def_code[i], &def_arg1[i], &def_arg2[i]);
1917 if (TREE_CODE (arg[i]) == SSA_NAME)
1918 def_arg_stmt[i] = SSA_NAME_DEF_STMT (arg[i]);
1921 else
1923 /* Handle signed rotate; the RSHIFT_EXPR has to be done
1924 in unsigned type but LSHIFT_EXPR could be signed. */
1925 i = (def_code[0] == LSHIFT_EXPR || def_code[0] == RSHIFT_EXPR);
1926 if (CONVERT_EXPR_CODE_P (def_code[i])
1927 && (def_code[1 - i] == LSHIFT_EXPR || def_code[1 - i] == RSHIFT_EXPR)
1928 && INTEGRAL_TYPE_P (TREE_TYPE (def_arg1[i]))
1929 && TYPE_PRECISION (rtype) == TYPE_PRECISION (TREE_TYPE (def_arg1[i]))
1930 && has_single_use (arg[i]))
1932 arg[i] = def_arg1[i];
1933 defcodefor_name (arg[i], &def_code[i], &def_arg1[i], &def_arg2[i]);
1934 if (TREE_CODE (arg[i]) == SSA_NAME)
1935 def_arg_stmt[i] = SSA_NAME_DEF_STMT (arg[i]);
1939 /* One operand has to be LSHIFT_EXPR and one RSHIFT_EXPR. */
1940 for (i = 0; i < 2; i++)
1941 if (def_code[i] != LSHIFT_EXPR && def_code[i] != RSHIFT_EXPR)
1942 return false;
1943 else if (!has_single_use (arg[i]))
1944 return false;
1945 if (def_code[0] == def_code[1])
1946 return false;
1948 /* If we've looked through narrowing conversions before, look through
1949 widening conversions from unsigned type with the same precision
1950 as rtype here. */
1951 if (TYPE_PRECISION (TREE_TYPE (def_arg1[0])) != TYPE_PRECISION (rtype))
1952 for (i = 0; i < 2; i++)
1954 tree tem;
1955 enum tree_code code;
1956 defcodefor_name (def_arg1[i], &code, &tem, NULL);
1957 if (!CONVERT_EXPR_CODE_P (code)
1958 || !INTEGRAL_TYPE_P (TREE_TYPE (tem))
1959 || TYPE_PRECISION (TREE_TYPE (tem)) != TYPE_PRECISION (rtype))
1960 return false;
1961 def_arg1[i] = tem;
1963 /* Both shifts have to use the same first operand. */
1964 if (!operand_equal_for_phi_arg_p (def_arg1[0], def_arg1[1])
1965 || !types_compatible_p (TREE_TYPE (def_arg1[0]),
1966 TREE_TYPE (def_arg1[1])))
1968 if ((TYPE_PRECISION (TREE_TYPE (def_arg1[0]))
1969 != TYPE_PRECISION (TREE_TYPE (def_arg1[1])))
1970 || (TYPE_UNSIGNED (TREE_TYPE (def_arg1[0]))
1971 == TYPE_UNSIGNED (TREE_TYPE (def_arg1[1]))))
1972 return false;
1974 /* Handle signed rotate; the RSHIFT_EXPR has to be done
1975 in unsigned type but LSHIFT_EXPR could be signed. */
1976 i = def_code[0] != RSHIFT_EXPR;
1977 if (!TYPE_UNSIGNED (TREE_TYPE (def_arg1[i])))
1978 return false;
1980 tree tem;
1981 enum tree_code code;
1982 defcodefor_name (def_arg1[i], &code, &tem, NULL);
1983 if (!CONVERT_EXPR_CODE_P (code)
1984 || !INTEGRAL_TYPE_P (TREE_TYPE (tem))
1985 || TYPE_PRECISION (TREE_TYPE (tem)) != TYPE_PRECISION (rtype))
1986 return false;
1987 def_arg1[i] = tem;
1988 if (!operand_equal_for_phi_arg_p (def_arg1[0], def_arg1[1])
1989 || !types_compatible_p (TREE_TYPE (def_arg1[0]),
1990 TREE_TYPE (def_arg1[1])))
1991 return false;
1993 else if (!TYPE_UNSIGNED (TREE_TYPE (def_arg1[0])))
1994 return false;
1996 /* CNT1 + CNT2 == B case above. */
1997 if (tree_fits_uhwi_p (def_arg2[0])
1998 && tree_fits_uhwi_p (def_arg2[1])
1999 && tree_to_uhwi (def_arg2[0])
2000 + tree_to_uhwi (def_arg2[1]) == TYPE_PRECISION (rtype))
2001 rotcnt = def_arg2[0];
2002 else if (TREE_CODE (def_arg2[0]) != SSA_NAME
2003 || TREE_CODE (def_arg2[1]) != SSA_NAME)
2004 return false;
2005 else
2007 tree cdef_arg1[2], cdef_arg2[2], def_arg2_alt[2];
2008 enum tree_code cdef_code[2];
2009 gimple *def_arg_alt_stmt[2] = { NULL, NULL };
2010 int check_range = 0;
2011 gimple *check_range_stmt = NULL;
2012 /* Look through conversion of the shift count argument.
2013 The C/C++ FE cast any shift count argument to integer_type_node.
2014 The only problem might be if the shift count type maximum value
2015 is equal or smaller than number of bits in rtype. */
2016 for (i = 0; i < 2; i++)
2018 def_arg2_alt[i] = def_arg2[i];
2019 defcodefor_name (def_arg2[i], &cdef_code[i],
2020 &cdef_arg1[i], &cdef_arg2[i]);
2021 if (CONVERT_EXPR_CODE_P (cdef_code[i])
2022 && INTEGRAL_TYPE_P (TREE_TYPE (cdef_arg1[i]))
2023 && TYPE_PRECISION (TREE_TYPE (cdef_arg1[i]))
2024 > floor_log2 (TYPE_PRECISION (rtype))
2025 && type_has_mode_precision_p (TREE_TYPE (cdef_arg1[i])))
2027 def_arg2_alt[i] = cdef_arg1[i];
2028 if (TREE_CODE (def_arg2[i]) == SSA_NAME)
2029 def_arg_alt_stmt[i] = SSA_NAME_DEF_STMT (def_arg2[i]);
2030 defcodefor_name (def_arg2_alt[i], &cdef_code[i],
2031 &cdef_arg1[i], &cdef_arg2[i]);
2033 else
2034 def_arg_alt_stmt[i] = def_arg_stmt[i];
2036 for (i = 0; i < 2; i++)
2037 /* Check for one shift count being Y and the other B - Y,
2038 with optional casts. */
2039 if (cdef_code[i] == MINUS_EXPR
2040 && tree_fits_shwi_p (cdef_arg1[i])
2041 && tree_to_shwi (cdef_arg1[i]) == TYPE_PRECISION (rtype)
2042 && TREE_CODE (cdef_arg2[i]) == SSA_NAME)
2044 tree tem;
2045 enum tree_code code;
2047 if (cdef_arg2[i] == def_arg2[1 - i]
2048 || cdef_arg2[i] == def_arg2_alt[1 - i])
2050 rotcnt = cdef_arg2[i];
2051 check_range = -1;
2052 if (cdef_arg2[i] == def_arg2[1 - i])
2053 check_range_stmt = def_arg_stmt[1 - i];
2054 else
2055 check_range_stmt = def_arg_alt_stmt[1 - i];
2056 break;
2058 defcodefor_name (cdef_arg2[i], &code, &tem, NULL);
2059 if (CONVERT_EXPR_CODE_P (code)
2060 && INTEGRAL_TYPE_P (TREE_TYPE (tem))
2061 && TYPE_PRECISION (TREE_TYPE (tem))
2062 > floor_log2 (TYPE_PRECISION (rtype))
2063 && type_has_mode_precision_p (TREE_TYPE (tem))
2064 && (tem == def_arg2[1 - i]
2065 || tem == def_arg2_alt[1 - i]))
2067 rotcnt = tem;
2068 check_range = -1;
2069 if (tem == def_arg2[1 - i])
2070 check_range_stmt = def_arg_stmt[1 - i];
2071 else
2072 check_range_stmt = def_arg_alt_stmt[1 - i];
2073 break;
2076 /* The above sequence isn't safe for Y being 0,
2077 because then one of the shifts triggers undefined behavior.
2078 This alternative is safe even for rotation count of 0.
2079 One shift count is Y and the other (-Y) & (B - 1).
2080 Or one shift count is Y & (B - 1) and the other (-Y) & (B - 1). */
2081 else if (cdef_code[i] == BIT_AND_EXPR
2082 && pow2p_hwi (TYPE_PRECISION (rtype))
2083 && tree_fits_shwi_p (cdef_arg2[i])
2084 && tree_to_shwi (cdef_arg2[i])
2085 == TYPE_PRECISION (rtype) - 1
2086 && TREE_CODE (cdef_arg1[i]) == SSA_NAME
2087 && gimple_assign_rhs_code (stmt) == BIT_IOR_EXPR)
2089 tree tem;
2090 enum tree_code code;
2092 defcodefor_name (cdef_arg1[i], &code, &tem, NULL);
2093 if (CONVERT_EXPR_CODE_P (code)
2094 && INTEGRAL_TYPE_P (TREE_TYPE (tem))
2095 && TYPE_PRECISION (TREE_TYPE (tem))
2096 > floor_log2 (TYPE_PRECISION (rtype))
2097 && type_has_mode_precision_p (TREE_TYPE (tem)))
2098 defcodefor_name (tem, &code, &tem, NULL);
2100 if (code == NEGATE_EXPR)
2102 if (tem == def_arg2[1 - i] || tem == def_arg2_alt[1 - i])
2104 rotcnt = tem;
2105 check_range = 1;
2106 if (tem == def_arg2[1 - i])
2107 check_range_stmt = def_arg_stmt[1 - i];
2108 else
2109 check_range_stmt = def_arg_alt_stmt[1 - i];
2110 break;
2112 tree tem2;
2113 defcodefor_name (tem, &code, &tem2, NULL);
2114 if (CONVERT_EXPR_CODE_P (code)
2115 && INTEGRAL_TYPE_P (TREE_TYPE (tem2))
2116 && TYPE_PRECISION (TREE_TYPE (tem2))
2117 > floor_log2 (TYPE_PRECISION (rtype))
2118 && type_has_mode_precision_p (TREE_TYPE (tem2)))
2120 if (tem2 == def_arg2[1 - i]
2121 || tem2 == def_arg2_alt[1 - i])
2123 rotcnt = tem2;
2124 check_range = 1;
2125 if (tem2 == def_arg2[1 - i])
2126 check_range_stmt = def_arg_stmt[1 - i];
2127 else
2128 check_range_stmt = def_arg_alt_stmt[1 - i];
2129 break;
2132 else
2133 tem2 = NULL_TREE;
2135 if (cdef_code[1 - i] == BIT_AND_EXPR
2136 && tree_fits_shwi_p (cdef_arg2[1 - i])
2137 && tree_to_shwi (cdef_arg2[1 - i])
2138 == TYPE_PRECISION (rtype) - 1
2139 && TREE_CODE (cdef_arg1[1 - i]) == SSA_NAME)
2141 if (tem == cdef_arg1[1 - i]
2142 || tem2 == cdef_arg1[1 - i])
2144 rotcnt = def_arg2[1 - i];
2145 break;
2147 tree tem3;
2148 defcodefor_name (cdef_arg1[1 - i], &code, &tem3, NULL);
2149 if (CONVERT_EXPR_CODE_P (code)
2150 && INTEGRAL_TYPE_P (TREE_TYPE (tem3))
2151 && TYPE_PRECISION (TREE_TYPE (tem3))
2152 > floor_log2 (TYPE_PRECISION (rtype))
2153 && type_has_mode_precision_p (TREE_TYPE (tem3)))
2155 if (tem == tem3 || tem2 == tem3)
2157 rotcnt = def_arg2[1 - i];
2158 break;
2164 if (check_range && wider_prec > TYPE_PRECISION (rtype))
2166 if (TREE_CODE (rotcnt) != SSA_NAME)
2167 return false;
2168 int_range_max r;
2169 range_query *q = get_range_query (cfun);
2170 if (q == get_global_range_query ())
2171 q = enable_ranger (cfun);
2172 if (!q->range_of_expr (r, rotcnt, check_range_stmt))
2174 if (check_range > 0)
2175 return false;
2176 r.set_varying (TREE_TYPE (rotcnt));
2178 int prec = TYPE_PRECISION (TREE_TYPE (rotcnt));
2179 signop sign = TYPE_SIGN (TREE_TYPE (rotcnt));
2180 wide_int min = wide_int::from (TYPE_PRECISION (rtype), prec, sign);
2181 wide_int max = wide_int::from (wider_prec - 1, prec, sign);
2182 if (check_range < 0)
2183 max = min;
2184 int_range<1> r2 (TREE_TYPE (rotcnt), min, max);
2185 r.intersect (r2);
2186 if (!r.undefined_p ())
2188 if (check_range > 0)
2190 int_range_max r3;
2191 for (int i = TYPE_PRECISION (rtype) + 1; i < wider_prec;
2192 i += TYPE_PRECISION (rtype))
2194 int j = i + TYPE_PRECISION (rtype) - 2;
2195 min = wide_int::from (i, prec, sign);
2196 max = wide_int::from (MIN (j, wider_prec - 1),
2197 prec, sign);
2198 int_range<1> r4 (TREE_TYPE (rotcnt), min, max);
2199 r3.union_ (r4);
2201 r.intersect (r3);
2202 if (!r.undefined_p ())
2203 return false;
2205 add_masking = true;
2208 if (rotcnt == NULL_TREE)
2209 return false;
2210 swapped_p = i != 1;
2213 if (!useless_type_conversion_p (TREE_TYPE (def_arg2[0]),
2214 TREE_TYPE (rotcnt)))
2216 g = gimple_build_assign (make_ssa_name (TREE_TYPE (def_arg2[0])),
2217 NOP_EXPR, rotcnt);
2218 gsi_insert_before (gsi, g, GSI_SAME_STMT);
2219 rotcnt = gimple_assign_lhs (g);
2221 if (add_masking)
2223 g = gimple_build_assign (make_ssa_name (TREE_TYPE (rotcnt)),
2224 BIT_AND_EXPR, rotcnt,
2225 build_int_cst (TREE_TYPE (rotcnt),
2226 TYPE_PRECISION (rtype) - 1));
2227 gsi_insert_before (gsi, g, GSI_SAME_STMT);
2228 rotcnt = gimple_assign_lhs (g);
2230 lhs = gimple_assign_lhs (stmt);
2231 if (!useless_type_conversion_p (rtype, TREE_TYPE (def_arg1[0])))
2232 lhs = make_ssa_name (TREE_TYPE (def_arg1[0]));
2233 g = gimple_build_assign (lhs,
2234 ((def_code[0] == LSHIFT_EXPR) ^ swapped_p)
2235 ? LROTATE_EXPR : RROTATE_EXPR, def_arg1[0], rotcnt);
2236 if (!useless_type_conversion_p (rtype, TREE_TYPE (def_arg1[0])))
2238 gsi_insert_before (gsi, g, GSI_SAME_STMT);
2239 g = gimple_build_assign (gimple_assign_lhs (stmt), NOP_EXPR, lhs);
2241 gsi_replace (gsi, g, false);
2242 return true;
2246 /* Check whether an array contains a valid ctz table. */
2247 static bool
2248 check_ctz_array (tree ctor, unsigned HOST_WIDE_INT mulc,
2249 HOST_WIDE_INT &zero_val, unsigned shift, unsigned bits)
2251 tree elt, idx;
2252 unsigned HOST_WIDE_INT i, mask;
2253 unsigned matched = 0;
2255 mask = ((HOST_WIDE_INT_1U << (bits - shift)) - 1) << shift;
2257 zero_val = 0;
2259 FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (ctor), i, idx, elt)
2261 if (TREE_CODE (idx) != INTEGER_CST || TREE_CODE (elt) != INTEGER_CST)
2262 return false;
2263 if (i > bits * 2)
2264 return false;
2266 unsigned HOST_WIDE_INT index = tree_to_shwi (idx);
2267 HOST_WIDE_INT val = tree_to_shwi (elt);
2269 if (index == 0)
2271 zero_val = val;
2272 matched++;
2275 if (val >= 0 && val < bits && (((mulc << val) & mask) >> shift) == index)
2276 matched++;
2278 if (matched > bits)
2279 return true;
2282 return false;
2285 /* Check whether a string contains a valid ctz table. */
2286 static bool
2287 check_ctz_string (tree string, unsigned HOST_WIDE_INT mulc,
2288 HOST_WIDE_INT &zero_val, unsigned shift, unsigned bits)
2290 unsigned HOST_WIDE_INT len = TREE_STRING_LENGTH (string);
2291 unsigned HOST_WIDE_INT mask;
2292 unsigned matched = 0;
2293 const unsigned char *p = (const unsigned char *) TREE_STRING_POINTER (string);
2295 if (len < bits || len > bits * 2)
2296 return false;
2298 mask = ((HOST_WIDE_INT_1U << (bits - shift)) - 1) << shift;
2300 zero_val = p[0];
2302 for (unsigned i = 0; i < len; i++)
2303 if (p[i] < bits && (((mulc << p[i]) & mask) >> shift) == i)
2304 matched++;
2306 return matched == bits;
2309 /* Recognize count trailing zeroes idiom.
2310 The canonical form is array[((x & -x) * C) >> SHIFT] where C is a magic
2311 constant which when multiplied by a power of 2 creates a unique value
2312 in the top 5 or 6 bits. This is then indexed into a table which maps it
2313 to the number of trailing zeroes. Array[0] is returned so the caller can
2314 emit an appropriate sequence depending on whether ctz (0) is defined on
2315 the target. */
2316 static bool
2317 optimize_count_trailing_zeroes (tree array_ref, tree x, tree mulc,
2318 tree tshift, HOST_WIDE_INT &zero_val)
2320 tree type = TREE_TYPE (array_ref);
2321 tree array = TREE_OPERAND (array_ref, 0);
2323 gcc_assert (TREE_CODE (mulc) == INTEGER_CST);
2324 gcc_assert (TREE_CODE (tshift) == INTEGER_CST);
2326 tree input_type = TREE_TYPE (x);
2327 unsigned input_bits = tree_to_shwi (TYPE_SIZE (input_type));
2329 /* Check the array element type is not wider than 32 bits and the input is
2330 an unsigned 32-bit or 64-bit type. */
2331 if (TYPE_PRECISION (type) > 32 || !TYPE_UNSIGNED (input_type))
2332 return false;
2333 if (input_bits != 32 && input_bits != 64)
2334 return false;
2336 if (!direct_internal_fn_supported_p (IFN_CTZ, input_type, OPTIMIZE_FOR_BOTH))
2337 return false;
2339 /* Check the lower bound of the array is zero. */
2340 tree low = array_ref_low_bound (array_ref);
2341 if (!low || !integer_zerop (low))
2342 return false;
2344 unsigned shiftval = tree_to_shwi (tshift);
2346 /* Check the shift extracts the top 5..7 bits. */
2347 if (shiftval < input_bits - 7 || shiftval > input_bits - 5)
2348 return false;
2350 tree ctor = ctor_for_folding (array);
2351 if (!ctor)
2352 return false;
2354 unsigned HOST_WIDE_INT val = tree_to_uhwi (mulc);
2356 if (TREE_CODE (ctor) == CONSTRUCTOR)
2357 return check_ctz_array (ctor, val, zero_val, shiftval, input_bits);
2359 if (TREE_CODE (ctor) == STRING_CST
2360 && TYPE_PRECISION (type) == CHAR_TYPE_SIZE)
2361 return check_ctz_string (ctor, val, zero_val, shiftval, input_bits);
2363 return false;
2366 /* Match.pd function to match the ctz expression. */
2367 extern bool gimple_ctz_table_index (tree, tree *, tree (*)(tree));
2369 static bool
2370 simplify_count_trailing_zeroes (gimple_stmt_iterator *gsi)
2372 gimple *stmt = gsi_stmt (*gsi);
2373 tree array_ref = gimple_assign_rhs1 (stmt);
2374 tree res_ops[3];
2375 HOST_WIDE_INT zero_val;
2377 gcc_checking_assert (TREE_CODE (array_ref) == ARRAY_REF);
2379 if (!gimple_ctz_table_index (TREE_OPERAND (array_ref, 1), &res_ops[0], NULL))
2380 return false;
2382 if (optimize_count_trailing_zeroes (array_ref, res_ops[0],
2383 res_ops[1], res_ops[2], zero_val))
2385 tree type = TREE_TYPE (res_ops[0]);
2386 HOST_WIDE_INT ctz_val = 0;
2387 HOST_WIDE_INT type_size = tree_to_shwi (TYPE_SIZE (type));
2388 bool zero_ok
2389 = CTZ_DEFINED_VALUE_AT_ZERO (SCALAR_INT_TYPE_MODE (type), ctz_val) == 2;
2390 int nargs = 2;
2392 /* If the input value can't be zero, don't special case ctz (0). */
2393 if (tree_expr_nonzero_p (res_ops[0]))
2395 zero_ok = true;
2396 zero_val = 0;
2397 ctz_val = 0;
2398 nargs = 1;
2401 /* Skip if there is no value defined at zero, or if we can't easily
2402 return the correct value for zero. */
2403 if (!zero_ok)
2404 return false;
2405 if (zero_val != ctz_val && !(zero_val == 0 && ctz_val == type_size))
2406 return false;
2408 gimple_seq seq = NULL;
2409 gimple *g;
2410 gcall *call
2411 = gimple_build_call_internal (IFN_CTZ, nargs, res_ops[0],
2412 nargs == 1 ? NULL_TREE
2413 : build_int_cst (integer_type_node,
2414 ctz_val));
2415 gimple_set_location (call, gimple_location (stmt));
2416 gimple_set_lhs (call, make_ssa_name (integer_type_node));
2417 gimple_seq_add_stmt (&seq, call);
2419 tree prev_lhs = gimple_call_lhs (call);
2421 /* Emit ctz (x) & 31 if ctz (0) is 32 but we need to return 0. */
2422 if (zero_val == 0 && ctz_val == type_size)
2424 g = gimple_build_assign (make_ssa_name (integer_type_node),
2425 BIT_AND_EXPR, prev_lhs,
2426 build_int_cst (integer_type_node,
2427 type_size - 1));
2428 gimple_set_location (g, gimple_location (stmt));
2429 gimple_seq_add_stmt (&seq, g);
2430 prev_lhs = gimple_assign_lhs (g);
2433 g = gimple_build_assign (gimple_assign_lhs (stmt), NOP_EXPR, prev_lhs);
2434 gimple_seq_add_stmt (&seq, g);
2435 gsi_replace_with_seq (gsi, seq, true);
2436 return true;
2439 return false;
2443 /* Combine an element access with a shuffle. Returns true if there were
2444 any changes made, else it returns false. */
2446 static bool
2447 simplify_bitfield_ref (gimple_stmt_iterator *gsi)
2449 gimple *stmt = gsi_stmt (*gsi);
2450 gimple *def_stmt;
2451 tree op, op0, op1;
2452 tree elem_type, type;
2453 tree p, m, tem;
2454 unsigned HOST_WIDE_INT nelts, idx;
2455 poly_uint64 size, elem_size;
2456 enum tree_code code;
2458 op = gimple_assign_rhs1 (stmt);
2459 gcc_checking_assert (TREE_CODE (op) == BIT_FIELD_REF);
2461 op0 = TREE_OPERAND (op, 0);
2462 if (TREE_CODE (op0) != SSA_NAME
2463 || TREE_CODE (TREE_TYPE (op0)) != VECTOR_TYPE)
2464 return false;
2466 def_stmt = get_prop_source_stmt (op0, false, NULL);
2467 if (!def_stmt || !can_propagate_from (def_stmt))
2468 return false;
2470 op1 = TREE_OPERAND (op, 1);
2471 code = gimple_assign_rhs_code (def_stmt);
2472 elem_type = TREE_TYPE (TREE_TYPE (op0));
2473 type = TREE_TYPE (op);
2474 /* Also handle vector type.
2475 .i.e.
2476 _7 = VEC_PERM_EXPR <_1, _1, { 2, 3, 2, 3 }>;
2477 _11 = BIT_FIELD_REF <_7, 64, 0>;
2481 _11 = BIT_FIELD_REF <_1, 64, 64>. */
2483 size = tree_to_poly_uint64 (TYPE_SIZE (type));
2484 if (maybe_ne (bit_field_size (op), size))
2485 return false;
2487 elem_size = tree_to_poly_uint64 (TYPE_SIZE (elem_type));
2488 if (code != VEC_PERM_EXPR
2489 || !constant_multiple_p (bit_field_offset (op), elem_size, &idx))
2490 return false;
2492 m = gimple_assign_rhs3 (def_stmt);
2493 if (TREE_CODE (m) != VECTOR_CST
2494 || !VECTOR_CST_NELTS (m).is_constant (&nelts))
2495 return false;
2497 /* One element. */
2498 if (known_eq (size, elem_size))
2499 idx = TREE_INT_CST_LOW (VECTOR_CST_ELT (m, idx)) % (2 * nelts);
2500 else
2502 unsigned HOST_WIDE_INT nelts_op;
2503 if (!constant_multiple_p (size, elem_size, &nelts_op)
2504 || !pow2p_hwi (nelts_op))
2505 return false;
2506 /* Clamp vec_perm_expr index. */
2507 unsigned start = TREE_INT_CST_LOW (vector_cst_elt (m, idx)) % (2 * nelts);
2508 unsigned end = TREE_INT_CST_LOW (vector_cst_elt (m, idx + nelts_op - 1))
2509 % (2 * nelts);
2510 /* Be in the same vector. */
2511 if ((start < nelts) != (end < nelts))
2512 return false;
2513 for (unsigned HOST_WIDE_INT i = 1; i != nelts_op; i++)
2515 /* Continuous area. */
2516 if (TREE_INT_CST_LOW (vector_cst_elt (m, idx + i)) % (2 * nelts) - 1
2517 != TREE_INT_CST_LOW (vector_cst_elt (m, idx + i - 1))
2518 % (2 * nelts))
2519 return false;
2521 /* Alignment not worse than before. */
2522 if (start % nelts_op)
2523 return false;
2524 idx = start;
2527 if (idx < nelts)
2528 p = gimple_assign_rhs1 (def_stmt);
2529 else
2531 p = gimple_assign_rhs2 (def_stmt);
2532 idx -= nelts;
2535 tem = build3 (BIT_FIELD_REF, TREE_TYPE (op),
2536 p, op1, bitsize_int (idx * elem_size));
2537 gimple_assign_set_rhs1 (stmt, tem);
2538 fold_stmt (gsi);
2539 update_stmt (gsi_stmt (*gsi));
2540 return true;
2543 /* Determine whether applying the 2 permutations (mask1 then mask2)
2544 gives back one of the input. */
2546 static int
2547 is_combined_permutation_identity (tree mask1, tree mask2)
2549 tree mask;
2550 unsigned HOST_WIDE_INT nelts, i, j;
2551 bool maybe_identity1 = true;
2552 bool maybe_identity2 = true;
2554 gcc_checking_assert (TREE_CODE (mask1) == VECTOR_CST
2555 && TREE_CODE (mask2) == VECTOR_CST);
2557 /* For VLA masks, check for the following pattern:
2558 v1 = VEC_PERM_EXPR (v0, ..., mask1)
2559 v2 = VEC_PERM_EXPR (v1, ..., mask2)
2561 v2 = v0
2562 if mask1 == mask2 == {nelts - 1, nelts - 2, ...}. */
2564 if (operand_equal_p (mask1, mask2, 0)
2565 && !VECTOR_CST_NELTS (mask1).is_constant ())
2567 vec_perm_builder builder;
2568 if (tree_to_vec_perm_builder (&builder, mask1))
2570 poly_uint64 nelts = TYPE_VECTOR_SUBPARTS (TREE_TYPE (mask1));
2571 vec_perm_indices sel (builder, 1, nelts);
2572 if (sel.series_p (0, 1, nelts - 1, -1))
2573 return 1;
2577 mask = fold_ternary (VEC_PERM_EXPR, TREE_TYPE (mask1), mask1, mask1, mask2);
2578 if (mask == NULL_TREE || TREE_CODE (mask) != VECTOR_CST)
2579 return 0;
2581 if (!VECTOR_CST_NELTS (mask).is_constant (&nelts))
2582 return 0;
2583 for (i = 0; i < nelts; i++)
2585 tree val = VECTOR_CST_ELT (mask, i);
2586 gcc_assert (TREE_CODE (val) == INTEGER_CST);
2587 j = TREE_INT_CST_LOW (val) & (2 * nelts - 1);
2588 if (j == i)
2589 maybe_identity2 = false;
2590 else if (j == i + nelts)
2591 maybe_identity1 = false;
2592 else
2593 return 0;
2595 return maybe_identity1 ? 1 : maybe_identity2 ? 2 : 0;
2598 /* Combine a shuffle with its arguments. Returns 1 if there were any
2599 changes made, 2 if cfg-cleanup needs to run. Else it returns 0. */
2601 static int
2602 simplify_permutation (gimple_stmt_iterator *gsi)
2604 gimple *stmt = gsi_stmt (*gsi);
2605 gimple *def_stmt = NULL;
2606 tree op0, op1, op2, op3, arg0, arg1;
2607 enum tree_code code, code2 = ERROR_MARK;
2608 bool single_use_op0 = false;
2610 gcc_checking_assert (gimple_assign_rhs_code (stmt) == VEC_PERM_EXPR);
2612 op0 = gimple_assign_rhs1 (stmt);
2613 op1 = gimple_assign_rhs2 (stmt);
2614 op2 = gimple_assign_rhs3 (stmt);
2616 if (TREE_CODE (op2) != VECTOR_CST)
2617 return 0;
2619 if (TREE_CODE (op0) == VECTOR_CST)
2621 code = VECTOR_CST;
2622 arg0 = op0;
2624 else if (TREE_CODE (op0) == SSA_NAME)
2626 def_stmt = get_prop_source_stmt (op0, false, &single_use_op0);
2627 if (!def_stmt)
2628 return 0;
2629 code = gimple_assign_rhs_code (def_stmt);
2630 if (code == VIEW_CONVERT_EXPR)
2632 tree rhs = gimple_assign_rhs1 (def_stmt);
2633 tree name = TREE_OPERAND (rhs, 0);
2634 if (TREE_CODE (name) != SSA_NAME)
2635 return 0;
2636 if (!has_single_use (name))
2637 single_use_op0 = false;
2638 /* Here we update the def_stmt through this VIEW_CONVERT_EXPR,
2639 but still keep the code to indicate it comes from
2640 VIEW_CONVERT_EXPR. */
2641 def_stmt = SSA_NAME_DEF_STMT (name);
2642 if (!def_stmt || !is_gimple_assign (def_stmt))
2643 return 0;
2644 if (gimple_assign_rhs_code (def_stmt) != CONSTRUCTOR)
2645 return 0;
2647 if (!can_propagate_from (def_stmt))
2648 return 0;
2649 arg0 = gimple_assign_rhs1 (def_stmt);
2651 else
2652 return 0;
2654 /* Two consecutive shuffles. */
2655 if (code == VEC_PERM_EXPR)
2657 tree orig;
2658 int ident;
2660 if (op0 != op1)
2661 return 0;
2662 op3 = gimple_assign_rhs3 (def_stmt);
2663 if (TREE_CODE (op3) != VECTOR_CST)
2664 return 0;
2665 ident = is_combined_permutation_identity (op3, op2);
2666 if (!ident)
2667 return 0;
2668 orig = (ident == 1) ? gimple_assign_rhs1 (def_stmt)
2669 : gimple_assign_rhs2 (def_stmt);
2670 gimple_assign_set_rhs1 (stmt, unshare_expr (orig));
2671 gimple_assign_set_rhs_code (stmt, TREE_CODE (orig));
2672 gimple_set_num_ops (stmt, 2);
2673 update_stmt (stmt);
2674 return remove_prop_source_from_use (op0) ? 2 : 1;
2676 else if (code == CONSTRUCTOR
2677 || code == VECTOR_CST
2678 || code == VIEW_CONVERT_EXPR)
2680 if (op0 != op1)
2682 if (TREE_CODE (op0) == SSA_NAME && !single_use_op0)
2683 return 0;
2685 if (TREE_CODE (op1) == VECTOR_CST)
2686 arg1 = op1;
2687 else if (TREE_CODE (op1) == SSA_NAME)
2689 gimple *def_stmt2 = get_prop_source_stmt (op1, true, NULL);
2690 if (!def_stmt2)
2691 return 0;
2692 code2 = gimple_assign_rhs_code (def_stmt2);
2693 if (code2 == VIEW_CONVERT_EXPR)
2695 tree rhs = gimple_assign_rhs1 (def_stmt2);
2696 tree name = TREE_OPERAND (rhs, 0);
2697 if (TREE_CODE (name) != SSA_NAME)
2698 return 0;
2699 if (!has_single_use (name))
2700 return 0;
2701 def_stmt2 = SSA_NAME_DEF_STMT (name);
2702 if (!def_stmt2 || !is_gimple_assign (def_stmt2))
2703 return 0;
2704 if (gimple_assign_rhs_code (def_stmt2) != CONSTRUCTOR)
2705 return 0;
2707 else if (code2 != CONSTRUCTOR && code2 != VECTOR_CST)
2708 return 0;
2709 if (!can_propagate_from (def_stmt2))
2710 return 0;
2711 arg1 = gimple_assign_rhs1 (def_stmt2);
2713 else
2714 return 0;
2716 else
2718 /* Already used twice in this statement. */
2719 if (TREE_CODE (op0) == SSA_NAME && num_imm_uses (op0) > 2)
2720 return 0;
2721 arg1 = arg0;
2724 /* If there are any VIEW_CONVERT_EXPRs found when finding permutation
2725 operands source, check whether it's valid to transform and prepare
2726 the required new operands. */
2727 if (code == VIEW_CONVERT_EXPR || code2 == VIEW_CONVERT_EXPR)
2729 /* Figure out the target vector type to which operands should be
2730 converted. If both are CONSTRUCTOR, the types should be the
2731 same, otherwise, use the one of CONSTRUCTOR. */
2732 tree tgt_type = NULL_TREE;
2733 if (code == VIEW_CONVERT_EXPR)
2735 gcc_assert (gimple_assign_rhs_code (def_stmt) == CONSTRUCTOR);
2736 code = CONSTRUCTOR;
2737 tgt_type = TREE_TYPE (arg0);
2739 if (code2 == VIEW_CONVERT_EXPR)
2741 tree arg1_type = TREE_TYPE (arg1);
2742 if (tgt_type == NULL_TREE)
2743 tgt_type = arg1_type;
2744 else if (tgt_type != arg1_type)
2745 return 0;
2748 if (!VECTOR_TYPE_P (tgt_type))
2749 return 0;
2750 tree op2_type = TREE_TYPE (op2);
2752 /* Figure out the shrunk factor. */
2753 poly_uint64 tgt_units = TYPE_VECTOR_SUBPARTS (tgt_type);
2754 poly_uint64 op2_units = TYPE_VECTOR_SUBPARTS (op2_type);
2755 if (maybe_gt (tgt_units, op2_units))
2756 return 0;
2757 unsigned int factor;
2758 if (!constant_multiple_p (op2_units, tgt_units, &factor))
2759 return 0;
2761 /* Build the new permutation control vector as target vector. */
2762 vec_perm_builder builder;
2763 if (!tree_to_vec_perm_builder (&builder, op2))
2764 return 0;
2765 vec_perm_indices indices (builder, 2, op2_units);
2766 vec_perm_indices new_indices;
2767 if (new_indices.new_shrunk_vector (indices, factor))
2769 tree mask_type = tgt_type;
2770 if (!VECTOR_INTEGER_TYPE_P (mask_type))
2772 tree elem_type = TREE_TYPE (mask_type);
2773 unsigned elem_size = TREE_INT_CST_LOW (TYPE_SIZE (elem_type));
2774 tree int_type = build_nonstandard_integer_type (elem_size, 0);
2775 mask_type = build_vector_type (int_type, tgt_units);
2777 op2 = vec_perm_indices_to_tree (mask_type, new_indices);
2779 else
2780 return 0;
2782 /* Convert the VECTOR_CST to the appropriate vector type. */
2783 if (tgt_type != TREE_TYPE (arg0))
2784 arg0 = fold_build1 (VIEW_CONVERT_EXPR, tgt_type, arg0);
2785 else if (tgt_type != TREE_TYPE (arg1))
2786 arg1 = fold_build1 (VIEW_CONVERT_EXPR, tgt_type, arg1);
2789 /* VIEW_CONVERT_EXPR should be updated to CONSTRUCTOR before. */
2790 gcc_assert (code == CONSTRUCTOR || code == VECTOR_CST);
2792 /* Shuffle of a constructor. */
2793 bool ret = false;
2794 tree res_type
2795 = build_vector_type (TREE_TYPE (TREE_TYPE (arg0)),
2796 TYPE_VECTOR_SUBPARTS (TREE_TYPE (op2)));
2797 tree opt = fold_ternary (VEC_PERM_EXPR, res_type, arg0, arg1, op2);
2798 if (!opt
2799 || (TREE_CODE (opt) != CONSTRUCTOR && TREE_CODE (opt) != VECTOR_CST))
2800 return 0;
2801 /* Found VIEW_CONVERT_EXPR before, need one explicit conversion. */
2802 if (res_type != TREE_TYPE (op0))
2804 tree name = make_ssa_name (TREE_TYPE (opt));
2805 gimple *ass_stmt = gimple_build_assign (name, opt);
2806 gsi_insert_before (gsi, ass_stmt, GSI_SAME_STMT);
2807 opt = build1 (VIEW_CONVERT_EXPR, TREE_TYPE (op0), name);
2809 gimple_assign_set_rhs_from_tree (gsi, opt);
2810 update_stmt (gsi_stmt (*gsi));
2811 if (TREE_CODE (op0) == SSA_NAME)
2812 ret = remove_prop_source_from_use (op0);
2813 if (op0 != op1 && TREE_CODE (op1) == SSA_NAME)
2814 ret |= remove_prop_source_from_use (op1);
2815 return ret ? 2 : 1;
2818 return 0;
2821 /* Get the BIT_FIELD_REF definition of VAL, if any, looking through
2822 conversions with code CONV_CODE or update it if still ERROR_MARK.
2823 Return NULL_TREE if no such matching def was found. */
2825 static tree
2826 get_bit_field_ref_def (tree val, enum tree_code &conv_code)
2828 if (TREE_CODE (val) != SSA_NAME)
2829 return NULL_TREE ;
2830 gimple *def_stmt = get_prop_source_stmt (val, false, NULL);
2831 if (!def_stmt)
2832 return NULL_TREE;
2833 enum tree_code code = gimple_assign_rhs_code (def_stmt);
2834 if (code == FLOAT_EXPR
2835 || code == FIX_TRUNC_EXPR
2836 || CONVERT_EXPR_CODE_P (code))
2838 tree op1 = gimple_assign_rhs1 (def_stmt);
2839 if (conv_code == ERROR_MARK)
2840 conv_code = code;
2841 else if (conv_code != code)
2842 return NULL_TREE;
2843 if (TREE_CODE (op1) != SSA_NAME)
2844 return NULL_TREE;
2845 def_stmt = SSA_NAME_DEF_STMT (op1);
2846 if (! is_gimple_assign (def_stmt))
2847 return NULL_TREE;
2848 code = gimple_assign_rhs_code (def_stmt);
2850 if (code != BIT_FIELD_REF)
2851 return NULL_TREE;
2852 return gimple_assign_rhs1 (def_stmt);
2855 /* Recognize a VEC_PERM_EXPR. Returns true if there were any changes. */
2857 static bool
2858 simplify_vector_constructor (gimple_stmt_iterator *gsi)
2860 gimple *stmt = gsi_stmt (*gsi);
2861 tree op, orig[2], type, elem_type;
2862 unsigned elem_size, i;
2863 unsigned HOST_WIDE_INT nelts;
2864 unsigned HOST_WIDE_INT refnelts;
2865 enum tree_code conv_code;
2866 constructor_elt *elt;
2868 op = gimple_assign_rhs1 (stmt);
2869 type = TREE_TYPE (op);
2870 gcc_checking_assert (TREE_CODE (op) == CONSTRUCTOR
2871 && TREE_CODE (type) == VECTOR_TYPE);
2873 if (!TYPE_VECTOR_SUBPARTS (type).is_constant (&nelts))
2874 return false;
2875 elem_type = TREE_TYPE (type);
2876 elem_size = TREE_INT_CST_LOW (TYPE_SIZE (elem_type));
2878 orig[0] = NULL;
2879 orig[1] = NULL;
2880 conv_code = ERROR_MARK;
2881 bool maybe_ident = true;
2882 bool maybe_blend[2] = { true, true };
2883 tree one_constant = NULL_TREE;
2884 tree one_nonconstant = NULL_TREE;
2885 auto_vec<tree> constants;
2886 constants.safe_grow_cleared (nelts, true);
2887 auto_vec<std::pair<unsigned, unsigned>, 64> elts;
2888 FOR_EACH_VEC_SAFE_ELT (CONSTRUCTOR_ELTS (op), i, elt)
2890 tree ref, op1;
2891 unsigned int elem;
2893 if (i >= nelts)
2894 return false;
2896 /* Look for elements extracted and possibly converted from
2897 another vector. */
2898 op1 = get_bit_field_ref_def (elt->value, conv_code);
2899 if (op1
2900 && TREE_CODE ((ref = TREE_OPERAND (op1, 0))) == SSA_NAME
2901 && VECTOR_TYPE_P (TREE_TYPE (ref))
2902 && useless_type_conversion_p (TREE_TYPE (op1),
2903 TREE_TYPE (TREE_TYPE (ref)))
2904 && constant_multiple_p (bit_field_offset (op1),
2905 bit_field_size (op1), &elem)
2906 && TYPE_VECTOR_SUBPARTS (TREE_TYPE (ref)).is_constant (&refnelts))
2908 unsigned int j;
2909 for (j = 0; j < 2; ++j)
2911 if (!orig[j])
2913 if (j == 0
2914 || useless_type_conversion_p (TREE_TYPE (orig[0]),
2915 TREE_TYPE (ref)))
2916 break;
2918 else if (ref == orig[j])
2919 break;
2921 /* Found a suitable vector element. */
2922 if (j < 2)
2924 orig[j] = ref;
2925 if (elem != i || j != 0)
2926 maybe_ident = false;
2927 if (elem != i)
2928 maybe_blend[j] = false;
2929 elts.safe_push (std::make_pair (j, elem));
2930 continue;
2932 /* Else fallthru. */
2934 /* Handle elements not extracted from a vector.
2935 1. constants by permuting with constant vector
2936 2. a unique non-constant element by permuting with a splat vector */
2937 if (orig[1]
2938 && orig[1] != error_mark_node)
2939 return false;
2940 orig[1] = error_mark_node;
2941 if (CONSTANT_CLASS_P (elt->value))
2943 if (one_nonconstant)
2944 return false;
2945 if (!one_constant)
2946 one_constant = elt->value;
2947 constants[i] = elt->value;
2949 else
2951 if (one_constant)
2952 return false;
2953 if (!one_nonconstant)
2954 one_nonconstant = elt->value;
2955 else if (!operand_equal_p (one_nonconstant, elt->value, 0))
2956 return false;
2958 elts.safe_push (std::make_pair (1, i));
2959 maybe_ident = false;
2961 if (i < nelts)
2962 return false;
2964 if (! orig[0]
2965 || ! VECTOR_TYPE_P (TREE_TYPE (orig[0])))
2966 return false;
2967 refnelts = TYPE_VECTOR_SUBPARTS (TREE_TYPE (orig[0])).to_constant ();
2968 /* We currently do not handle larger destination vectors. */
2969 if (refnelts < nelts)
2970 return false;
2972 if (maybe_ident)
2974 tree conv_src_type
2975 = (nelts != refnelts
2976 ? (conv_code != ERROR_MARK
2977 ? build_vector_type (TREE_TYPE (TREE_TYPE (orig[0])), nelts)
2978 : type)
2979 : TREE_TYPE (orig[0]));
2980 if (conv_code != ERROR_MARK
2981 && !supportable_convert_operation (conv_code, type, conv_src_type,
2982 &conv_code))
2984 /* Only few targets implement direct conversion patterns so try
2985 some simple special cases via VEC_[UN]PACK[_FLOAT]_LO_EXPR. */
2986 optab optab;
2987 insn_code icode;
2988 tree halfvectype, dblvectype;
2989 enum tree_code unpack_op;
2991 if (!BYTES_BIG_ENDIAN)
2992 unpack_op = (FLOAT_TYPE_P (TREE_TYPE (type))
2993 ? VEC_UNPACK_FLOAT_LO_EXPR
2994 : VEC_UNPACK_LO_EXPR);
2995 else
2996 unpack_op = (FLOAT_TYPE_P (TREE_TYPE (type))
2997 ? VEC_UNPACK_FLOAT_HI_EXPR
2998 : VEC_UNPACK_HI_EXPR);
3000 /* Conversions between DFP and FP have no special tree code
3001 but we cannot handle those since all relevant vector conversion
3002 optabs only have a single mode. */
3003 if (CONVERT_EXPR_CODE_P (conv_code)
3004 && FLOAT_TYPE_P (TREE_TYPE (type))
3005 && (DECIMAL_FLOAT_TYPE_P (TREE_TYPE (type))
3006 != DECIMAL_FLOAT_TYPE_P (TREE_TYPE (conv_src_type))))
3007 return false;
3009 if (CONVERT_EXPR_CODE_P (conv_code)
3010 && (2 * TYPE_PRECISION (TREE_TYPE (TREE_TYPE (orig[0])))
3011 == TYPE_PRECISION (TREE_TYPE (type)))
3012 && mode_for_vector (as_a <scalar_mode>
3013 (TYPE_MODE (TREE_TYPE (TREE_TYPE (orig[0])))),
3014 nelts * 2).exists ()
3015 && (dblvectype
3016 = build_vector_type (TREE_TYPE (TREE_TYPE (orig[0])),
3017 nelts * 2))
3018 /* Only use it for vector modes or for vector booleans
3019 represented as scalar bitmasks. See PR95528. */
3020 && (VECTOR_MODE_P (TYPE_MODE (dblvectype))
3021 || VECTOR_BOOLEAN_TYPE_P (dblvectype))
3022 && (optab = optab_for_tree_code (unpack_op,
3023 dblvectype,
3024 optab_default))
3025 && ((icode = optab_handler (optab, TYPE_MODE (dblvectype)))
3026 != CODE_FOR_nothing)
3027 && (insn_data[icode].operand[0].mode == TYPE_MODE (type)))
3029 gimple_seq stmts = NULL;
3030 tree dbl;
3031 if (refnelts == nelts)
3033 /* ??? Paradoxical subregs don't exist, so insert into
3034 the lower half of a wider zero vector. */
3035 dbl = gimple_build (&stmts, BIT_INSERT_EXPR, dblvectype,
3036 build_zero_cst (dblvectype), orig[0],
3037 bitsize_zero_node);
3039 else if (refnelts == 2 * nelts)
3040 dbl = orig[0];
3041 else
3042 dbl = gimple_build (&stmts, BIT_FIELD_REF, dblvectype,
3043 orig[0], TYPE_SIZE (dblvectype),
3044 bitsize_zero_node);
3045 gsi_insert_seq_before (gsi, stmts, GSI_SAME_STMT);
3046 gimple_assign_set_rhs_with_ops (gsi, unpack_op, dbl);
3048 else if (CONVERT_EXPR_CODE_P (conv_code)
3049 && (TYPE_PRECISION (TREE_TYPE (TREE_TYPE (orig[0])))
3050 == 2 * TYPE_PRECISION (TREE_TYPE (type)))
3051 && mode_for_vector (as_a <scalar_mode>
3052 (TYPE_MODE
3053 (TREE_TYPE (TREE_TYPE (orig[0])))),
3054 nelts / 2).exists ()
3055 && (halfvectype
3056 = build_vector_type (TREE_TYPE (TREE_TYPE (orig[0])),
3057 nelts / 2))
3058 /* Only use it for vector modes or for vector booleans
3059 represented as scalar bitmasks. See PR95528. */
3060 && (VECTOR_MODE_P (TYPE_MODE (halfvectype))
3061 || VECTOR_BOOLEAN_TYPE_P (halfvectype))
3062 && (optab = optab_for_tree_code (VEC_PACK_TRUNC_EXPR,
3063 halfvectype,
3064 optab_default))
3065 && ((icode = optab_handler (optab, TYPE_MODE (halfvectype)))
3066 != CODE_FOR_nothing)
3067 && (insn_data[icode].operand[0].mode == TYPE_MODE (type)))
3069 gimple_seq stmts = NULL;
3070 tree low = gimple_build (&stmts, BIT_FIELD_REF, halfvectype,
3071 orig[0], TYPE_SIZE (halfvectype),
3072 bitsize_zero_node);
3073 tree hig = gimple_build (&stmts, BIT_FIELD_REF, halfvectype,
3074 orig[0], TYPE_SIZE (halfvectype),
3075 TYPE_SIZE (halfvectype));
3076 gsi_insert_seq_before (gsi, stmts, GSI_SAME_STMT);
3077 gimple_assign_set_rhs_with_ops (gsi, VEC_PACK_TRUNC_EXPR,
3078 low, hig);
3080 else
3081 return false;
3082 update_stmt (gsi_stmt (*gsi));
3083 return true;
3085 if (nelts != refnelts)
3087 gassign *lowpart
3088 = gimple_build_assign (make_ssa_name (conv_src_type),
3089 build3 (BIT_FIELD_REF, conv_src_type,
3090 orig[0], TYPE_SIZE (conv_src_type),
3091 bitsize_zero_node));
3092 gsi_insert_before (gsi, lowpart, GSI_SAME_STMT);
3093 orig[0] = gimple_assign_lhs (lowpart);
3095 if (conv_code == ERROR_MARK)
3097 tree src_type = TREE_TYPE (orig[0]);
3098 if (!useless_type_conversion_p (type, src_type))
3100 gcc_assert (known_eq (TYPE_VECTOR_SUBPARTS (type),
3101 TYPE_VECTOR_SUBPARTS (src_type))
3102 && useless_type_conversion_p (TREE_TYPE (type),
3103 TREE_TYPE (src_type)));
3104 tree rhs = build1 (VIEW_CONVERT_EXPR, type, orig[0]);
3105 orig[0] = make_ssa_name (type);
3106 gassign *assign = gimple_build_assign (orig[0], rhs);
3107 gsi_insert_before (gsi, assign, GSI_SAME_STMT);
3109 gimple_assign_set_rhs_from_tree (gsi, orig[0]);
3111 else
3112 gimple_assign_set_rhs_with_ops (gsi, conv_code, orig[0],
3113 NULL_TREE, NULL_TREE);
3115 else
3117 /* If we combine a vector with a non-vector avoid cases where
3118 we'll obviously end up with more GIMPLE stmts which is when
3119 we'll later not fold this to a single insert into the vector
3120 and we had a single extract originally. See PR92819. */
3121 if (nelts == 2
3122 && refnelts > 2
3123 && orig[1] == error_mark_node
3124 && !maybe_blend[0])
3125 return false;
3126 tree mask_type, perm_type, conv_src_type;
3127 perm_type = TREE_TYPE (orig[0]);
3128 conv_src_type = (nelts == refnelts
3129 ? perm_type
3130 : build_vector_type (TREE_TYPE (perm_type), nelts));
3131 if (conv_code != ERROR_MARK
3132 && !supportable_convert_operation (conv_code, type, conv_src_type,
3133 &conv_code))
3134 return false;
3136 /* Now that we know the number of elements of the source build the
3137 permute vector.
3138 ??? When the second vector has constant values we can shuffle
3139 it and its source indexes to make the permutation supported.
3140 For now it mimics a blend. */
3141 vec_perm_builder sel (refnelts, refnelts, 1);
3142 bool all_same_p = true;
3143 for (i = 0; i < elts.length (); ++i)
3145 sel.quick_push (elts[i].second + elts[i].first * refnelts);
3146 all_same_p &= known_eq (sel[i], sel[0]);
3148 /* And fill the tail with "something". It's really don't care,
3149 and ideally we'd allow VEC_PERM to have a smaller destination
3150 vector. As a heuristic:
3152 (a) if what we have so far duplicates a single element, make the
3153 tail do the same
3155 (b) otherwise preserve a uniform orig[0]. This facilitates
3156 later pattern-matching of VEC_PERM_EXPR to a BIT_INSERT_EXPR. */
3157 for (; i < refnelts; ++i)
3158 sel.quick_push (all_same_p
3159 ? sel[0]
3160 : (elts[0].second == 0 && elts[0].first == 0
3161 ? 0 : refnelts) + i);
3162 vec_perm_indices indices (sel, orig[1] ? 2 : 1, refnelts);
3163 machine_mode vmode = TYPE_MODE (perm_type);
3164 if (!can_vec_perm_const_p (vmode, vmode, indices))
3165 return false;
3166 mask_type
3167 = build_vector_type (build_nonstandard_integer_type (elem_size, 1),
3168 refnelts);
3169 if (GET_MODE_CLASS (TYPE_MODE (mask_type)) != MODE_VECTOR_INT
3170 || maybe_ne (GET_MODE_SIZE (TYPE_MODE (mask_type)),
3171 GET_MODE_SIZE (TYPE_MODE (perm_type))))
3172 return false;
3173 tree op2 = vec_perm_indices_to_tree (mask_type, indices);
3174 bool converted_orig1 = false;
3175 gimple_seq stmts = NULL;
3176 if (!orig[1])
3177 orig[1] = orig[0];
3178 else if (orig[1] == error_mark_node
3179 && one_nonconstant)
3181 /* ??? We can see if we can safely convert to the original
3182 element type. */
3183 converted_orig1 = conv_code != ERROR_MARK;
3184 orig[1] = gimple_build_vector_from_val (&stmts, UNKNOWN_LOCATION,
3185 converted_orig1
3186 ? type : perm_type,
3187 one_nonconstant);
3189 else if (orig[1] == error_mark_node)
3191 /* ??? See if we can convert the vector to the original type. */
3192 converted_orig1 = conv_code != ERROR_MARK;
3193 unsigned n = converted_orig1 ? nelts : refnelts;
3194 tree_vector_builder vec (converted_orig1
3195 ? type : perm_type, n, 1);
3196 for (unsigned i = 0; i < n; ++i)
3197 if (i < nelts && constants[i])
3198 vec.quick_push (constants[i]);
3199 else
3200 /* ??? Push a don't-care value. */
3201 vec.quick_push (one_constant);
3202 orig[1] = vec.build ();
3204 tree blend_op2 = NULL_TREE;
3205 if (converted_orig1)
3207 /* Make sure we can do a blend in the target type. */
3208 vec_perm_builder sel (nelts, nelts, 1);
3209 for (i = 0; i < elts.length (); ++i)
3210 sel.quick_push (elts[i].first
3211 ? elts[i].second + nelts : i);
3212 vec_perm_indices indices (sel, 2, nelts);
3213 machine_mode vmode = TYPE_MODE (type);
3214 if (!can_vec_perm_const_p (vmode, vmode, indices))
3215 return false;
3216 mask_type
3217 = build_vector_type (build_nonstandard_integer_type (elem_size, 1),
3218 nelts);
3219 if (GET_MODE_CLASS (TYPE_MODE (mask_type)) != MODE_VECTOR_INT
3220 || maybe_ne (GET_MODE_SIZE (TYPE_MODE (mask_type)),
3221 GET_MODE_SIZE (TYPE_MODE (type))))
3222 return false;
3223 blend_op2 = vec_perm_indices_to_tree (mask_type, indices);
3225 tree orig1_for_perm
3226 = converted_orig1 ? build_zero_cst (perm_type) : orig[1];
3227 tree res = gimple_build (&stmts, VEC_PERM_EXPR, perm_type,
3228 orig[0], orig1_for_perm, op2);
3229 if (nelts != refnelts)
3230 res = gimple_build (&stmts, BIT_FIELD_REF,
3231 conv_code != ERROR_MARK ? conv_src_type : type,
3232 res, TYPE_SIZE (type), bitsize_zero_node);
3233 if (conv_code != ERROR_MARK)
3234 res = gimple_build (&stmts, conv_code, type, res);
3235 else if (!useless_type_conversion_p (type, TREE_TYPE (res)))
3237 gcc_assert (known_eq (TYPE_VECTOR_SUBPARTS (type),
3238 TYPE_VECTOR_SUBPARTS (perm_type))
3239 && useless_type_conversion_p (TREE_TYPE (type),
3240 TREE_TYPE (perm_type)));
3241 res = gimple_build (&stmts, VIEW_CONVERT_EXPR, type, res);
3243 /* Blend in the actual constant. */
3244 if (converted_orig1)
3245 res = gimple_build (&stmts, VEC_PERM_EXPR, type,
3246 res, orig[1], blend_op2);
3247 gsi_insert_seq_before (gsi, stmts, GSI_SAME_STMT);
3248 gimple_assign_set_rhs_with_ops (gsi, SSA_NAME, res);
3250 update_stmt (gsi_stmt (*gsi));
3251 return true;
3254 /* Prepare a TARGET_MEM_REF ref so that it can be subsetted as
3255 lvalue. This splits out an address computation stmt before *GSI
3256 and returns a MEM_REF wrapping the address. */
3258 static tree
3259 prepare_target_mem_ref_lvalue (tree ref, gimple_stmt_iterator *gsi)
3261 if (TREE_CODE (TREE_OPERAND (ref, 0)) == ADDR_EXPR)
3262 mark_addressable (TREE_OPERAND (TREE_OPERAND (ref, 0), 0));
3263 tree ptrtype = build_pointer_type (TREE_TYPE (ref));
3264 tree tem = make_ssa_name (ptrtype);
3265 gimple *new_stmt
3266 = gimple_build_assign (tem, build1 (ADDR_EXPR, TREE_TYPE (tem),
3267 unshare_expr (ref)));
3268 gsi_insert_before (gsi, new_stmt, GSI_SAME_STMT);
3269 ref = build2_loc (EXPR_LOCATION (ref),
3270 MEM_REF, TREE_TYPE (ref), tem,
3271 build_int_cst (TREE_TYPE (TREE_OPERAND (ref, 1)), 0));
3272 return ref;
3275 /* Rewrite the vector load at *GSI to component-wise loads if the load
3276 is only used in BIT_FIELD_REF extractions with eventual intermediate
3277 widening. */
3279 static void
3280 optimize_vector_load (gimple_stmt_iterator *gsi)
3282 gimple *stmt = gsi_stmt (*gsi);
3283 tree lhs = gimple_assign_lhs (stmt);
3284 tree rhs = gimple_assign_rhs1 (stmt);
3286 /* Gather BIT_FIELD_REFs to rewrite, looking through
3287 VEC_UNPACK_{LO,HI}_EXPR. */
3288 use_operand_p use_p;
3289 imm_use_iterator iter;
3290 bool rewrite = true;
3291 auto_vec<gimple *, 8> bf_stmts;
3292 auto_vec<tree, 8> worklist;
3293 worklist.quick_push (lhs);
3296 tree def = worklist.pop ();
3297 unsigned HOST_WIDE_INT def_eltsize
3298 = TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (TREE_TYPE (def))));
3299 FOR_EACH_IMM_USE_FAST (use_p, iter, def)
3301 gimple *use_stmt = USE_STMT (use_p);
3302 if (is_gimple_debug (use_stmt))
3303 continue;
3304 if (!is_gimple_assign (use_stmt))
3306 rewrite = false;
3307 break;
3309 enum tree_code use_code = gimple_assign_rhs_code (use_stmt);
3310 tree use_rhs = gimple_assign_rhs1 (use_stmt);
3311 if (use_code == BIT_FIELD_REF
3312 && TREE_OPERAND (use_rhs, 0) == def
3313 /* If its on the VEC_UNPACK_{HI,LO}_EXPR
3314 def need to verify it is element aligned. */
3315 && (def == lhs
3316 || (known_eq (bit_field_size (use_rhs), def_eltsize)
3317 && constant_multiple_p (bit_field_offset (use_rhs),
3318 def_eltsize)
3319 /* We can simulate the VEC_UNPACK_{HI,LO}_EXPR
3320 via a NOP_EXPR only for integral types.
3321 ??? Support VEC_UNPACK_FLOAT_{HI,LO}_EXPR. */
3322 && INTEGRAL_TYPE_P (TREE_TYPE (use_rhs)))))
3324 bf_stmts.safe_push (use_stmt);
3325 continue;
3327 /* Walk through one level of VEC_UNPACK_{LO,HI}_EXPR. */
3328 if (def == lhs
3329 && (use_code == VEC_UNPACK_HI_EXPR
3330 || use_code == VEC_UNPACK_LO_EXPR)
3331 && use_rhs == lhs)
3333 worklist.safe_push (gimple_assign_lhs (use_stmt));
3334 continue;
3336 rewrite = false;
3337 break;
3339 if (!rewrite)
3340 break;
3342 while (!worklist.is_empty ());
3344 if (!rewrite)
3346 gsi_next (gsi);
3347 return;
3349 /* We now have all ultimate uses of the load to rewrite in bf_stmts. */
3351 /* Prepare the original ref to be wrapped in adjusted BIT_FIELD_REFs.
3352 For TARGET_MEM_REFs we have to separate the LEA from the reference. */
3353 tree load_rhs = rhs;
3354 if (TREE_CODE (load_rhs) == TARGET_MEM_REF)
3355 load_rhs = prepare_target_mem_ref_lvalue (load_rhs, gsi);
3357 /* Rewrite the BIT_FIELD_REFs to be actual loads, re-emitting them at
3358 the place of the original load. */
3359 for (gimple *use_stmt : bf_stmts)
3361 tree bfr = gimple_assign_rhs1 (use_stmt);
3362 tree new_rhs = unshare_expr (load_rhs);
3363 if (TREE_OPERAND (bfr, 0) != lhs)
3365 /* When the BIT_FIELD_REF is on the promoted vector we have to
3366 adjust it and emit a conversion afterwards. */
3367 gimple *def_stmt
3368 = SSA_NAME_DEF_STMT (TREE_OPERAND (bfr, 0));
3369 enum tree_code def_code
3370 = gimple_assign_rhs_code (def_stmt);
3372 /* The adjusted BIT_FIELD_REF is of the promotion source
3373 vector size and at half of the offset... */
3374 new_rhs = fold_build3 (BIT_FIELD_REF,
3375 TREE_TYPE (TREE_TYPE (lhs)),
3376 new_rhs,
3377 TYPE_SIZE (TREE_TYPE (TREE_TYPE (lhs))),
3378 size_binop (EXACT_DIV_EXPR,
3379 TREE_OPERAND (bfr, 2),
3380 bitsize_int (2)));
3381 /* ... and offsetted by half of the vector if VEC_UNPACK_HI_EXPR. */
3382 if (def_code == (!BYTES_BIG_ENDIAN
3383 ? VEC_UNPACK_HI_EXPR : VEC_UNPACK_LO_EXPR))
3384 TREE_OPERAND (new_rhs, 2)
3385 = size_binop (PLUS_EXPR, TREE_OPERAND (new_rhs, 2),
3386 size_binop (EXACT_DIV_EXPR,
3387 TYPE_SIZE (TREE_TYPE (lhs)),
3388 bitsize_int (2)));
3389 tree tem = make_ssa_name (TREE_TYPE (TREE_TYPE (lhs)));
3390 gimple *new_stmt = gimple_build_assign (tem, new_rhs);
3391 location_t loc = gimple_location (use_stmt);
3392 gimple_set_location (new_stmt, loc);
3393 gsi_insert_before (gsi, new_stmt, GSI_SAME_STMT);
3394 /* Perform scalar promotion. */
3395 new_stmt = gimple_build_assign (gimple_assign_lhs (use_stmt),
3396 NOP_EXPR, tem);
3397 gimple_set_location (new_stmt, loc);
3398 gsi_insert_before (gsi, new_stmt, GSI_SAME_STMT);
3400 else
3402 /* When the BIT_FIELD_REF is on the original load result
3403 we can just wrap that. */
3404 tree new_rhs = fold_build3 (BIT_FIELD_REF, TREE_TYPE (bfr),
3405 unshare_expr (load_rhs),
3406 TREE_OPERAND (bfr, 1),
3407 TREE_OPERAND (bfr, 2));
3408 gimple *new_stmt = gimple_build_assign (gimple_assign_lhs (use_stmt),
3409 new_rhs);
3410 location_t loc = gimple_location (use_stmt);
3411 gimple_set_location (new_stmt, loc);
3412 gsi_insert_before (gsi, new_stmt, GSI_SAME_STMT);
3414 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3415 unlink_stmt_vdef (use_stmt);
3416 gsi_remove (&gsi2, true);
3419 /* Finally get rid of the intermediate stmts. */
3420 gimple *use_stmt;
3421 FOR_EACH_IMM_USE_STMT (use_stmt, iter, lhs)
3423 if (is_gimple_debug (use_stmt))
3425 if (gimple_debug_bind_p (use_stmt))
3427 gimple_debug_bind_reset_value (use_stmt);
3428 update_stmt (use_stmt);
3430 continue;
3432 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3433 unlink_stmt_vdef (use_stmt);
3434 release_defs (use_stmt);
3435 gsi_remove (&gsi2, true);
3437 /* And the original load. */
3438 release_defs (stmt);
3439 gsi_remove (gsi, true);
3443 /* Primitive "lattice" function for gimple_simplify. */
3445 static tree
3446 fwprop_ssa_val (tree name)
3448 /* First valueize NAME. */
3449 if (TREE_CODE (name) == SSA_NAME
3450 && SSA_NAME_VERSION (name) < lattice.length ())
3452 tree val = lattice[SSA_NAME_VERSION (name)];
3453 if (val)
3454 name = val;
3456 /* We continue matching along SSA use-def edges for SSA names
3457 that are not single-use. Currently there are no patterns
3458 that would cause any issues with that. */
3459 return name;
3462 /* Main entry point for the forward propagation and statement combine
3463 optimizer. */
3465 namespace {
3467 const pass_data pass_data_forwprop =
3469 GIMPLE_PASS, /* type */
3470 "forwprop", /* name */
3471 OPTGROUP_NONE, /* optinfo_flags */
3472 TV_TREE_FORWPROP, /* tv_id */
3473 ( PROP_cfg | PROP_ssa ), /* properties_required */
3474 0, /* properties_provided */
3475 0, /* properties_destroyed */
3476 0, /* todo_flags_start */
3477 TODO_update_ssa, /* todo_flags_finish */
3480 class pass_forwprop : public gimple_opt_pass
3482 public:
3483 pass_forwprop (gcc::context *ctxt)
3484 : gimple_opt_pass (pass_data_forwprop, ctxt)
3487 /* opt_pass methods: */
3488 opt_pass * clone () final override { return new pass_forwprop (m_ctxt); }
3489 bool gate (function *) final override { return flag_tree_forwprop; }
3490 unsigned int execute (function *) final override;
3492 }; // class pass_forwprop
3494 unsigned int
3495 pass_forwprop::execute (function *fun)
3497 unsigned int todoflags = 0;
3499 cfg_changed = false;
3501 calculate_dominance_info (CDI_DOMINATORS);
3503 /* Combine stmts with the stmts defining their operands. Do that
3504 in an order that guarantees visiting SSA defs before SSA uses. */
3505 lattice.create (num_ssa_names);
3506 lattice.quick_grow_cleared (num_ssa_names);
3507 int *postorder = XNEWVEC (int, n_basic_blocks_for_fn (fun));
3508 int postorder_num = pre_and_rev_post_order_compute_fn (fun, NULL,
3509 postorder, false);
3510 int *bb_to_rpo = XNEWVEC (int, last_basic_block_for_fn (fun));
3511 for (int i = 0; i < postorder_num; ++i)
3513 bb_to_rpo[postorder[i]] = i;
3514 edge_iterator ei;
3515 edge e;
3516 FOR_EACH_EDGE (e, ei, BASIC_BLOCK_FOR_FN (fun, postorder[i])->succs)
3517 e->flags &= ~EDGE_EXECUTABLE;
3519 single_succ_edge (BASIC_BLOCK_FOR_FN (fun, ENTRY_BLOCK))->flags
3520 |= EDGE_EXECUTABLE;
3521 auto_vec<gimple *, 4> to_fixup;
3522 auto_vec<gimple *, 32> to_remove;
3523 auto_vec<unsigned, 32> to_remove_defs;
3524 auto_vec<std::pair<int, int>, 10> edges_to_remove;
3525 auto_bitmap simple_dce_worklist;
3526 auto_bitmap need_ab_cleanup;
3527 to_purge = BITMAP_ALLOC (NULL);
3528 for (int i = 0; i < postorder_num; ++i)
3530 gimple_stmt_iterator gsi;
3531 basic_block bb = BASIC_BLOCK_FOR_FN (fun, postorder[i]);
3532 edge_iterator ei;
3533 edge e;
3535 /* Skip processing not executable blocks. We could improve
3536 single_use tracking by at least unlinking uses from unreachable
3537 blocks but since blocks with uses are not processed in a
3538 meaningful order this is probably not worth it. */
3539 bool any = false;
3540 FOR_EACH_EDGE (e, ei, bb->preds)
3542 if ((e->flags & EDGE_EXECUTABLE)
3543 /* We can handle backedges in natural loops correctly but
3544 for irreducible regions we have to take all backedges
3545 conservatively when we did not visit the source yet. */
3546 || (bb_to_rpo[e->src->index] > i
3547 && !dominated_by_p (CDI_DOMINATORS, e->src, e->dest)))
3549 any = true;
3550 break;
3553 if (!any)
3554 continue;
3556 /* Record degenerate PHIs in the lattice. */
3557 for (gphi_iterator si = gsi_start_phis (bb); !gsi_end_p (si);
3558 gsi_next (&si))
3560 gphi *phi = si.phi ();
3561 tree res = gimple_phi_result (phi);
3562 if (virtual_operand_p (res))
3563 continue;
3565 tree first = NULL_TREE;
3566 bool all_same = true;
3567 edge_iterator ei;
3568 edge e;
3569 FOR_EACH_EDGE (e, ei, bb->preds)
3571 /* Ignore not executable forward edges. */
3572 if (!(e->flags & EDGE_EXECUTABLE))
3574 if (bb_to_rpo[e->src->index] < i)
3575 continue;
3576 /* Avoid equivalences from backedges - while we might
3577 be able to make irreducible regions reducible and
3578 thus turning a back into a forward edge we do not
3579 want to deal with the intermediate SSA issues that
3580 exposes. */
3581 all_same = false;
3583 tree use = PHI_ARG_DEF_FROM_EDGE (phi, e);
3584 if (use == res)
3585 /* The PHI result can also appear on a backedge, if so
3586 we can ignore this case for the purpose of determining
3587 the singular value. */
3589 else if (! first)
3590 first = use;
3591 else if (! operand_equal_p (first, use, 0))
3593 all_same = false;
3594 break;
3597 if (all_same)
3599 if (may_propagate_copy (res, first))
3600 to_remove_defs.safe_push (SSA_NAME_VERSION (res));
3601 fwprop_set_lattice_val (res, first);
3605 /* Apply forward propagation to all stmts in the basic-block.
3606 Note we update GSI within the loop as necessary. */
3607 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); )
3609 gimple *stmt = gsi_stmt (gsi);
3610 tree lhs, rhs;
3611 enum tree_code code;
3613 if (!is_gimple_assign (stmt))
3615 gsi_next (&gsi);
3616 continue;
3619 lhs = gimple_assign_lhs (stmt);
3620 rhs = gimple_assign_rhs1 (stmt);
3621 code = gimple_assign_rhs_code (stmt);
3622 if (TREE_CODE (lhs) != SSA_NAME
3623 || has_zero_uses (lhs))
3625 gsi_next (&gsi);
3626 continue;
3629 /* If this statement sets an SSA_NAME to an address,
3630 try to propagate the address into the uses of the SSA_NAME. */
3631 if ((code == ADDR_EXPR
3632 /* Handle pointer conversions on invariant addresses
3633 as well, as this is valid gimple. */
3634 || (CONVERT_EXPR_CODE_P (code)
3635 && TREE_CODE (rhs) == ADDR_EXPR
3636 && POINTER_TYPE_P (TREE_TYPE (lhs))))
3637 && TREE_CODE (TREE_OPERAND (rhs, 0)) != TARGET_MEM_REF)
3639 tree base = get_base_address (TREE_OPERAND (rhs, 0));
3640 if ((!base
3641 || !DECL_P (base)
3642 || decl_address_invariant_p (base))
3643 && !stmt_references_abnormal_ssa_name (stmt)
3644 && forward_propagate_addr_expr (lhs, rhs, true))
3646 fwprop_invalidate_lattice (gimple_get_lhs (stmt));
3647 release_defs (stmt);
3648 gsi_remove (&gsi, true);
3650 else
3651 gsi_next (&gsi);
3653 else if (code == POINTER_PLUS_EXPR)
3655 tree off = gimple_assign_rhs2 (stmt);
3656 if (TREE_CODE (off) == INTEGER_CST
3657 && can_propagate_from (stmt)
3658 && !simple_iv_increment_p (stmt)
3659 /* ??? Better adjust the interface to that function
3660 instead of building new trees here. */
3661 && forward_propagate_addr_expr
3662 (lhs,
3663 build1_loc (gimple_location (stmt),
3664 ADDR_EXPR, TREE_TYPE (rhs),
3665 fold_build2 (MEM_REF,
3666 TREE_TYPE (TREE_TYPE (rhs)),
3667 rhs,
3668 fold_convert (ptr_type_node,
3669 off))), true))
3671 fwprop_invalidate_lattice (gimple_get_lhs (stmt));
3672 release_defs (stmt);
3673 gsi_remove (&gsi, true);
3675 else if (is_gimple_min_invariant (rhs))
3677 /* Make sure to fold &a[0] + off_1 here. */
3678 fold_stmt_inplace (&gsi);
3679 update_stmt (stmt);
3680 if (gimple_assign_rhs_code (stmt) == POINTER_PLUS_EXPR)
3681 gsi_next (&gsi);
3683 else
3684 gsi_next (&gsi);
3686 else if (TREE_CODE (TREE_TYPE (lhs)) == COMPLEX_TYPE
3687 && gimple_assign_load_p (stmt)
3688 && !gimple_has_volatile_ops (stmt)
3689 && (TREE_CODE (gimple_assign_rhs1 (stmt))
3690 != TARGET_MEM_REF)
3691 && !stmt_can_throw_internal (fun, stmt))
3693 /* Rewrite loads used only in real/imagpart extractions to
3694 component-wise loads. */
3695 use_operand_p use_p;
3696 imm_use_iterator iter;
3697 bool rewrite = true;
3698 FOR_EACH_IMM_USE_FAST (use_p, iter, lhs)
3700 gimple *use_stmt = USE_STMT (use_p);
3701 if (is_gimple_debug (use_stmt))
3702 continue;
3703 if (!is_gimple_assign (use_stmt)
3704 || (gimple_assign_rhs_code (use_stmt) != REALPART_EXPR
3705 && gimple_assign_rhs_code (use_stmt) != IMAGPART_EXPR)
3706 || TREE_OPERAND (gimple_assign_rhs1 (use_stmt), 0) != lhs)
3708 rewrite = false;
3709 break;
3712 if (rewrite)
3714 gimple *use_stmt;
3715 FOR_EACH_IMM_USE_STMT (use_stmt, iter, lhs)
3717 if (is_gimple_debug (use_stmt))
3719 if (gimple_debug_bind_p (use_stmt))
3721 gimple_debug_bind_reset_value (use_stmt);
3722 update_stmt (use_stmt);
3724 continue;
3727 tree new_rhs = build1 (gimple_assign_rhs_code (use_stmt),
3728 TREE_TYPE (TREE_TYPE (rhs)),
3729 unshare_expr (rhs));
3730 gimple *new_stmt
3731 = gimple_build_assign (gimple_assign_lhs (use_stmt),
3732 new_rhs);
3734 location_t loc = gimple_location (use_stmt);
3735 gimple_set_location (new_stmt, loc);
3736 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3737 unlink_stmt_vdef (use_stmt);
3738 gsi_remove (&gsi2, true);
3740 gsi_insert_before (&gsi, new_stmt, GSI_SAME_STMT);
3743 release_defs (stmt);
3744 gsi_remove (&gsi, true);
3746 else
3747 gsi_next (&gsi);
3749 else if (TREE_CODE (TREE_TYPE (lhs)) == VECTOR_TYPE
3750 && (TYPE_MODE (TREE_TYPE (lhs)) == BLKmode
3751 /* After vector lowering rewrite all loads, but
3752 initially do not since this conflicts with
3753 vector CONSTRUCTOR to shuffle optimization. */
3754 || (fun->curr_properties & PROP_gimple_lvec))
3755 && gimple_assign_load_p (stmt)
3756 && !gimple_has_volatile_ops (stmt)
3757 && !stmt_can_throw_internal (fun, stmt)
3758 && (!VAR_P (rhs) || !DECL_HARD_REGISTER (rhs)))
3759 optimize_vector_load (&gsi);
3761 else if (code == COMPLEX_EXPR)
3763 /* Rewrite stores of a single-use complex build expression
3764 to component-wise stores. */
3765 use_operand_p use_p;
3766 gimple *use_stmt, *def1, *def2;
3767 tree rhs2;
3768 if (single_imm_use (lhs, &use_p, &use_stmt)
3769 && gimple_store_p (use_stmt)
3770 && !gimple_has_volatile_ops (use_stmt)
3771 && is_gimple_assign (use_stmt)
3772 && (TREE_CODE (TREE_TYPE (gimple_assign_lhs (use_stmt)))
3773 == COMPLEX_TYPE)
3774 && (TREE_CODE (gimple_assign_lhs (use_stmt))
3775 != TARGET_MEM_REF))
3777 tree use_lhs = gimple_assign_lhs (use_stmt);
3778 if (auto_var_p (use_lhs))
3779 DECL_NOT_GIMPLE_REG_P (use_lhs) = 1;
3780 tree new_lhs = build1 (REALPART_EXPR,
3781 TREE_TYPE (TREE_TYPE (use_lhs)),
3782 unshare_expr (use_lhs));
3783 gimple *new_stmt = gimple_build_assign (new_lhs, rhs);
3784 location_t loc = gimple_location (use_stmt);
3785 gimple_set_location (new_stmt, loc);
3786 gimple_set_vuse (new_stmt, gimple_vuse (use_stmt));
3787 gimple_set_vdef (new_stmt, make_ssa_name (gimple_vop (fun)));
3788 SSA_NAME_DEF_STMT (gimple_vdef (new_stmt)) = new_stmt;
3789 gimple_set_vuse (use_stmt, gimple_vdef (new_stmt));
3790 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3791 gsi_insert_before (&gsi2, new_stmt, GSI_SAME_STMT);
3793 new_lhs = build1 (IMAGPART_EXPR,
3794 TREE_TYPE (TREE_TYPE (use_lhs)),
3795 unshare_expr (use_lhs));
3796 gimple_assign_set_lhs (use_stmt, new_lhs);
3797 gimple_assign_set_rhs1 (use_stmt, gimple_assign_rhs2 (stmt));
3798 update_stmt (use_stmt);
3800 release_defs (stmt);
3801 gsi_remove (&gsi, true);
3803 /* Rewrite a component-wise load of a complex to a complex
3804 load if the components are not used separately. */
3805 else if (TREE_CODE (rhs) == SSA_NAME
3806 && has_single_use (rhs)
3807 && ((rhs2 = gimple_assign_rhs2 (stmt)), true)
3808 && TREE_CODE (rhs2) == SSA_NAME
3809 && has_single_use (rhs2)
3810 && (def1 = SSA_NAME_DEF_STMT (rhs),
3811 gimple_assign_load_p (def1))
3812 && (def2 = SSA_NAME_DEF_STMT (rhs2),
3813 gimple_assign_load_p (def2))
3814 && (gimple_vuse (def1) == gimple_vuse (def2))
3815 && !gimple_has_volatile_ops (def1)
3816 && !gimple_has_volatile_ops (def2)
3817 && !stmt_can_throw_internal (fun, def1)
3818 && !stmt_can_throw_internal (fun, def2)
3819 && gimple_assign_rhs_code (def1) == REALPART_EXPR
3820 && gimple_assign_rhs_code (def2) == IMAGPART_EXPR
3821 && operand_equal_p (TREE_OPERAND (gimple_assign_rhs1
3822 (def1), 0),
3823 TREE_OPERAND (gimple_assign_rhs1
3824 (def2), 0)))
3826 tree cl = TREE_OPERAND (gimple_assign_rhs1 (def1), 0);
3827 gimple_assign_set_rhs_from_tree (&gsi, unshare_expr (cl));
3828 gcc_assert (gsi_stmt (gsi) == stmt);
3829 gimple_set_vuse (stmt, gimple_vuse (def1));
3830 gimple_set_modified (stmt, true);
3831 gimple_stmt_iterator gsi2 = gsi_for_stmt (def1);
3832 gsi_remove (&gsi, false);
3833 gsi_insert_after (&gsi2, stmt, GSI_SAME_STMT);
3835 else
3836 gsi_next (&gsi);
3838 else if (code == CONSTRUCTOR
3839 && VECTOR_TYPE_P (TREE_TYPE (rhs))
3840 && TYPE_MODE (TREE_TYPE (rhs)) == BLKmode
3841 && CONSTRUCTOR_NELTS (rhs) > 0
3842 && (!VECTOR_TYPE_P (TREE_TYPE (CONSTRUCTOR_ELT (rhs, 0)->value))
3843 || (TYPE_MODE (TREE_TYPE (CONSTRUCTOR_ELT (rhs, 0)->value))
3844 != BLKmode)))
3846 /* Rewrite stores of a single-use vector constructors
3847 to component-wise stores if the mode isn't supported. */
3848 use_operand_p use_p;
3849 gimple *use_stmt;
3850 if (single_imm_use (lhs, &use_p, &use_stmt)
3851 && gimple_store_p (use_stmt)
3852 && !gimple_has_volatile_ops (use_stmt)
3853 && !stmt_can_throw_internal (fun, use_stmt)
3854 && is_gimple_assign (use_stmt))
3856 tree elt_t = TREE_TYPE (CONSTRUCTOR_ELT (rhs, 0)->value);
3857 unsigned HOST_WIDE_INT elt_w
3858 = tree_to_uhwi (TYPE_SIZE (elt_t));
3859 unsigned HOST_WIDE_INT n
3860 = tree_to_uhwi (TYPE_SIZE (TREE_TYPE (rhs)));
3861 tree use_lhs = gimple_assign_lhs (use_stmt);
3862 if (auto_var_p (use_lhs))
3863 DECL_NOT_GIMPLE_REG_P (use_lhs) = 1;
3864 else if (TREE_CODE (use_lhs) == TARGET_MEM_REF)
3866 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3867 use_lhs = prepare_target_mem_ref_lvalue (use_lhs, &gsi2);
3869 for (unsigned HOST_WIDE_INT bi = 0; bi < n; bi += elt_w)
3871 unsigned HOST_WIDE_INT ci = bi / elt_w;
3872 tree new_rhs;
3873 if (ci < CONSTRUCTOR_NELTS (rhs))
3874 new_rhs = CONSTRUCTOR_ELT (rhs, ci)->value;
3875 else
3876 new_rhs = build_zero_cst (elt_t);
3877 tree new_lhs = build3 (BIT_FIELD_REF,
3878 elt_t,
3879 unshare_expr (use_lhs),
3880 bitsize_int (elt_w),
3881 bitsize_int (bi));
3882 gimple *new_stmt = gimple_build_assign (new_lhs, new_rhs);
3883 location_t loc = gimple_location (use_stmt);
3884 gimple_set_location (new_stmt, loc);
3885 gimple_set_vuse (new_stmt, gimple_vuse (use_stmt));
3886 gimple_set_vdef (new_stmt,
3887 make_ssa_name (gimple_vop (fun)));
3888 SSA_NAME_DEF_STMT (gimple_vdef (new_stmt)) = new_stmt;
3889 gimple_set_vuse (use_stmt, gimple_vdef (new_stmt));
3890 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3891 gsi_insert_before (&gsi2, new_stmt, GSI_SAME_STMT);
3893 gimple_stmt_iterator gsi2 = gsi_for_stmt (use_stmt);
3894 unlink_stmt_vdef (use_stmt);
3895 release_defs (use_stmt);
3896 gsi_remove (&gsi2, true);
3897 release_defs (stmt);
3898 gsi_remove (&gsi, true);
3900 else
3901 gsi_next (&gsi);
3903 else
3904 gsi_next (&gsi);
3907 /* Combine stmts with the stmts defining their operands.
3908 Note we update GSI within the loop as necessary. */
3909 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
3911 gimple *stmt = gsi_stmt (gsi);
3913 /* Mark stmt as potentially needing revisiting. */
3914 gimple_set_plf (stmt, GF_PLF_1, false);
3916 bool can_make_abnormal_goto = (is_gimple_call (stmt)
3917 && stmt_can_make_abnormal_goto (stmt));
3919 /* Substitute from our lattice. We need to do so only once. */
3920 bool substituted_p = false;
3921 use_operand_p usep;
3922 ssa_op_iter iter;
3923 FOR_EACH_SSA_USE_OPERAND (usep, stmt, iter, SSA_OP_USE)
3925 tree use = USE_FROM_PTR (usep);
3926 tree val = fwprop_ssa_val (use);
3927 if (val && val != use)
3929 if (!is_gimple_debug (stmt))
3930 bitmap_set_bit (simple_dce_worklist, SSA_NAME_VERSION (use));
3931 if (may_propagate_copy (use, val))
3933 propagate_value (usep, val);
3934 substituted_p = true;
3938 if (substituted_p
3939 && is_gimple_assign (stmt)
3940 && gimple_assign_rhs_code (stmt) == ADDR_EXPR)
3941 recompute_tree_invariant_for_addr_expr (gimple_assign_rhs1 (stmt));
3942 if (substituted_p
3943 && can_make_abnormal_goto
3944 && !stmt_can_make_abnormal_goto (stmt))
3945 bitmap_set_bit (need_ab_cleanup, bb->index);
3947 bool changed;
3950 gimple *orig_stmt = stmt = gsi_stmt (gsi);
3951 bool was_noreturn = (is_gimple_call (stmt)
3952 && gimple_call_noreturn_p (stmt));
3953 changed = false;
3955 auto_vec<tree, 8> uses;
3956 FOR_EACH_SSA_USE_OPERAND (usep, stmt, iter, SSA_OP_USE)
3957 if (uses.space (1))
3958 uses.quick_push (USE_FROM_PTR (usep));
3960 if (fold_stmt (&gsi, fwprop_ssa_val, simple_dce_worklist))
3962 changed = true;
3963 stmt = gsi_stmt (gsi);
3964 /* Cleanup the CFG if we simplified a condition to
3965 true or false. */
3966 if (gcond *cond = dyn_cast <gcond *> (stmt))
3967 if (gimple_cond_true_p (cond)
3968 || gimple_cond_false_p (cond))
3969 cfg_changed = true;
3970 /* Queue old uses for simple DCE if not debug statement. */
3971 if (!is_gimple_debug (stmt))
3972 for (tree use : uses)
3973 if (TREE_CODE (use) == SSA_NAME
3974 && !SSA_NAME_IS_DEFAULT_DEF (use))
3975 bitmap_set_bit (simple_dce_worklist,
3976 SSA_NAME_VERSION (use));
3979 if (changed || substituted_p)
3981 if (maybe_clean_or_replace_eh_stmt (orig_stmt, stmt))
3982 bitmap_set_bit (to_purge, bb->index);
3983 if (!was_noreturn
3984 && is_gimple_call (stmt) && gimple_call_noreturn_p (stmt))
3985 to_fixup.safe_push (stmt);
3986 update_stmt (stmt);
3987 substituted_p = false;
3990 switch (gimple_code (stmt))
3992 case GIMPLE_ASSIGN:
3994 tree rhs1 = gimple_assign_rhs1 (stmt);
3995 enum tree_code code = gimple_assign_rhs_code (stmt);
3997 if (TREE_CODE_CLASS (code) == tcc_comparison)
3999 int did_something;
4000 did_something = forward_propagate_into_comparison (&gsi);
4001 if (maybe_clean_or_replace_eh_stmt (stmt, gsi_stmt (gsi)))
4002 bitmap_set_bit (to_purge, bb->index);
4003 if (did_something == 2)
4004 cfg_changed = true;
4005 changed = did_something != 0;
4007 else if ((code == PLUS_EXPR
4008 || code == BIT_IOR_EXPR
4009 || code == BIT_XOR_EXPR)
4010 && simplify_rotate (&gsi))
4011 changed = true;
4012 else if (code == VEC_PERM_EXPR)
4014 int did_something = simplify_permutation (&gsi);
4015 if (did_something == 2)
4016 cfg_changed = true;
4017 changed = did_something != 0;
4019 else if (code == BIT_FIELD_REF)
4020 changed = simplify_bitfield_ref (&gsi);
4021 else if (code == CONSTRUCTOR
4022 && TREE_CODE (TREE_TYPE (rhs1)) == VECTOR_TYPE)
4023 changed = simplify_vector_constructor (&gsi);
4024 else if (code == ARRAY_REF)
4025 changed = simplify_count_trailing_zeroes (&gsi);
4026 break;
4029 case GIMPLE_SWITCH:
4030 changed = simplify_gimple_switch (as_a <gswitch *> (stmt),
4031 edges_to_remove);
4032 break;
4034 case GIMPLE_COND:
4036 int did_something = forward_propagate_into_gimple_cond
4037 (as_a <gcond *> (stmt));
4038 if (did_something == 2)
4039 cfg_changed = true;
4040 changed = did_something != 0;
4041 break;
4044 case GIMPLE_CALL:
4046 tree callee = gimple_call_fndecl (stmt);
4047 if (callee != NULL_TREE
4048 && fndecl_built_in_p (callee, BUILT_IN_NORMAL))
4049 changed = simplify_builtin_call (&gsi, callee);
4050 break;
4053 default:;
4056 if (changed)
4058 /* If the stmt changed then re-visit it and the statements
4059 inserted before it. */
4060 for (; !gsi_end_p (gsi); gsi_prev (&gsi))
4061 if (gimple_plf (gsi_stmt (gsi), GF_PLF_1))
4062 break;
4063 if (gsi_end_p (gsi))
4064 gsi = gsi_start_bb (bb);
4065 else
4066 gsi_next (&gsi);
4069 while (changed);
4071 /* Stmt no longer needs to be revisited. */
4072 stmt = gsi_stmt (gsi);
4073 gcc_checking_assert (!gimple_plf (stmt, GF_PLF_1));
4074 gimple_set_plf (stmt, GF_PLF_1, true);
4076 /* Fill up the lattice. */
4077 if (gimple_assign_single_p (stmt))
4079 tree lhs = gimple_assign_lhs (stmt);
4080 tree rhs = gimple_assign_rhs1 (stmt);
4081 if (TREE_CODE (lhs) == SSA_NAME)
4083 tree val = lhs;
4084 if (TREE_CODE (rhs) == SSA_NAME)
4085 val = fwprop_ssa_val (rhs);
4086 else if (is_gimple_min_invariant (rhs))
4087 val = rhs;
4088 /* If we can propagate the lattice-value mark the
4089 stmt for removal. */
4090 if (val != lhs
4091 && may_propagate_copy (lhs, val))
4092 to_remove_defs.safe_push (SSA_NAME_VERSION (lhs));
4093 fwprop_set_lattice_val (lhs, val);
4096 else if (gimple_nop_p (stmt))
4097 to_remove.safe_push (stmt);
4100 /* Substitute in destination PHI arguments. */
4101 FOR_EACH_EDGE (e, ei, bb->succs)
4102 for (gphi_iterator gsi = gsi_start_phis (e->dest);
4103 !gsi_end_p (gsi); gsi_next (&gsi))
4105 gphi *phi = gsi.phi ();
4106 use_operand_p use_p = PHI_ARG_DEF_PTR_FROM_EDGE (phi, e);
4107 tree arg = USE_FROM_PTR (use_p);
4108 if (TREE_CODE (arg) != SSA_NAME
4109 || virtual_operand_p (arg))
4110 continue;
4111 tree val = fwprop_ssa_val (arg);
4112 if (val != arg
4113 && may_propagate_copy (arg, val, !(e->flags & EDGE_ABNORMAL)))
4114 propagate_value (use_p, val);
4117 /* Mark outgoing exectuable edges. */
4118 if (edge e = find_taken_edge (bb, NULL))
4120 e->flags |= EDGE_EXECUTABLE;
4121 if (EDGE_COUNT (bb->succs) > 1)
4122 cfg_changed = true;
4124 else
4126 FOR_EACH_EDGE (e, ei, bb->succs)
4127 e->flags |= EDGE_EXECUTABLE;
4130 free (postorder);
4131 free (bb_to_rpo);
4132 lattice.release ();
4134 /* First remove chains of stmts where we check no uses remain. */
4135 simple_dce_from_worklist (simple_dce_worklist, to_purge);
4137 auto remove = [](gimple *stmt)
4139 if (dump_file && (dump_flags & TDF_DETAILS))
4141 fprintf (dump_file, "Removing dead stmt ");
4142 print_gimple_stmt (dump_file, stmt, 0);
4143 fprintf (dump_file, "\n");
4145 gimple_stmt_iterator gsi = gsi_for_stmt (stmt);
4146 if (gimple_code (stmt) == GIMPLE_PHI)
4147 remove_phi_node (&gsi, true);
4148 else
4150 unlink_stmt_vdef (stmt);
4151 gsi_remove (&gsi, true);
4152 release_defs (stmt);
4156 /* Then remove stmts we know we can remove even though we did not
4157 substitute in dead code regions, so uses can remain. Do so in reverse
4158 order to make debug stmt creation possible. */
4159 while (!to_remove_defs.is_empty())
4161 tree def = ssa_name (to_remove_defs.pop ());
4162 /* For example remove_prop_source_from_use can remove stmts queued
4163 for removal. Deal with this gracefully. */
4164 if (!def)
4165 continue;
4166 gimple *stmt = SSA_NAME_DEF_STMT (def);
4167 remove (stmt);
4170 /* Wipe other queued stmts that do not have SSA defs. */
4171 while (!to_remove.is_empty())
4173 gimple *stmt = to_remove.pop ();
4174 remove (stmt);
4177 /* Fixup stmts that became noreturn calls. This may require splitting
4178 blocks and thus isn't possible during the walk. Do this
4179 in reverse order so we don't inadvertedly remove a stmt we want to
4180 fixup by visiting a dominating now noreturn call first. */
4181 while (!to_fixup.is_empty ())
4183 gimple *stmt = to_fixup.pop ();
4184 if (dump_file && dump_flags & TDF_DETAILS)
4186 fprintf (dump_file, "Fixing up noreturn call ");
4187 print_gimple_stmt (dump_file, stmt, 0);
4188 fprintf (dump_file, "\n");
4190 cfg_changed |= fixup_noreturn_call (stmt);
4193 cfg_changed |= gimple_purge_all_dead_eh_edges (to_purge);
4194 cfg_changed |= gimple_purge_all_dead_abnormal_call_edges (need_ab_cleanup);
4195 BITMAP_FREE (to_purge);
4197 /* Remove edges queued from switch stmt simplification. */
4198 for (auto ep : edges_to_remove)
4200 basic_block src = BASIC_BLOCK_FOR_FN (fun, ep.first);
4201 basic_block dest = BASIC_BLOCK_FOR_FN (fun, ep.second);
4202 edge e;
4203 if (src && dest && (e = find_edge (src, dest)))
4205 free_dominance_info (CDI_DOMINATORS);
4206 remove_edge (e);
4207 cfg_changed = true;
4211 if (get_range_query (fun) != get_global_range_query ())
4212 disable_ranger (fun);
4214 if (cfg_changed)
4215 todoflags |= TODO_cleanup_cfg;
4217 return todoflags;
4220 } // anon namespace
4222 gimple_opt_pass *
4223 make_pass_forwprop (gcc::context *ctxt)
4225 return new pass_forwprop (ctxt);