OSDN Git Service

i386: Rewrite ix86_expand_vshuffle.
[pf3gnuchains/gcc-fork.git] / gcc / tree-ssa-phiopt.c
1 /* Optimization of PHI nodes by converting them into straightline code.
2    Copyright (C) 2004, 2005, 2006, 2007, 2008, 2009, 2010
3    Free Software Foundation, Inc.
4
5 This file is part of GCC.
6
7 GCC is free software; you can redistribute it and/or modify it
8 under the terms of the GNU General Public License as published by the
9 Free Software Foundation; either version 3, or (at your option) any
10 later version.
11
12 GCC is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15 for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3.  If not see
19 <http://www.gnu.org/licenses/>.  */
20
21 #include "config.h"
22 #include "system.h"
23 #include "coretypes.h"
24 #include "tm.h"
25 #include "ggc.h"
26 #include "tree.h"
27 #include "flags.h"
28 #include "tm_p.h"
29 #include "basic-block.h"
30 #include "timevar.h"
31 #include "tree-flow.h"
32 #include "tree-pass.h"
33 #include "tree-dump.h"
34 #include "langhooks.h"
35 #include "pointer-set.h"
36 #include "domwalk.h"
37 #include "cfgloop.h"
38 #include "tree-data-ref.h"
39
40 static unsigned int tree_ssa_phiopt (void);
41 static unsigned int tree_ssa_phiopt_worker (bool);
42 static bool conditional_replacement (basic_block, basic_block,
43                                      edge, edge, gimple, tree, tree);
44 static bool value_replacement (basic_block, basic_block,
45                                edge, edge, gimple, tree, tree);
46 static bool minmax_replacement (basic_block, basic_block,
47                                 edge, edge, gimple, tree, tree);
48 static bool abs_replacement (basic_block, basic_block,
49                              edge, edge, gimple, tree, tree);
50 static bool cond_store_replacement (basic_block, basic_block, edge, edge,
51                                     struct pointer_set_t *);
52 static bool cond_if_else_store_replacement (basic_block, basic_block, basic_block);
53 static struct pointer_set_t * get_non_trapping (void);
54 static void replace_phi_edge_with_variable (basic_block, edge, gimple, tree);
55
56 /* This pass tries to replaces an if-then-else block with an
57    assignment.  We have four kinds of transformations.  Some of these
58    transformations are also performed by the ifcvt RTL optimizer.
59
60    Conditional Replacement
61    -----------------------
62
63    This transformation, implemented in conditional_replacement,
64    replaces
65
66      bb0:
67       if (cond) goto bb2; else goto bb1;
68      bb1:
69      bb2:
70       x = PHI <0 (bb1), 1 (bb0), ...>;
71
72    with
73
74      bb0:
75       x' = cond;
76       goto bb2;
77      bb2:
78       x = PHI <x' (bb0), ...>;
79
80    We remove bb1 as it becomes unreachable.  This occurs often due to
81    gimplification of conditionals.
82
83    Value Replacement
84    -----------------
85
86    This transformation, implemented in value_replacement, replaces
87
88      bb0:
89        if (a != b) goto bb2; else goto bb1;
90      bb1:
91      bb2:
92        x = PHI <a (bb1), b (bb0), ...>;
93
94    with
95
96      bb0:
97      bb2:
98        x = PHI <b (bb0), ...>;
99
100    This opportunity can sometimes occur as a result of other
101    optimizations.
102
103    ABS Replacement
104    ---------------
105
106    This transformation, implemented in abs_replacement, replaces
107
108      bb0:
109        if (a >= 0) goto bb2; else goto bb1;
110      bb1:
111        x = -a;
112      bb2:
113        x = PHI <x (bb1), a (bb0), ...>;
114
115    with
116
117      bb0:
118        x' = ABS_EXPR< a >;
119      bb2:
120        x = PHI <x' (bb0), ...>;
121
122    MIN/MAX Replacement
123    -------------------
124
125    This transformation, minmax_replacement replaces
126
127      bb0:
128        if (a <= b) goto bb2; else goto bb1;
129      bb1:
130      bb2:
131        x = PHI <b (bb1), a (bb0), ...>;
132
133    with
134
135      bb0:
136        x' = MIN_EXPR (a, b)
137      bb2:
138        x = PHI <x' (bb0), ...>;
139
140    A similar transformation is done for MAX_EXPR.  */
141
142 static unsigned int
143 tree_ssa_phiopt (void)
144 {
145   return tree_ssa_phiopt_worker (false);
146 }
147
148 /* This pass tries to transform conditional stores into unconditional
149    ones, enabling further simplifications with the simpler then and else
150    blocks.  In particular it replaces this:
151
152      bb0:
153        if (cond) goto bb2; else goto bb1;
154      bb1:
155        *p = RHS;
156      bb2:
157
158    with
159
160      bb0:
161        if (cond) goto bb1; else goto bb2;
162      bb1:
163        condtmp' = *p;
164      bb2:
165        condtmp = PHI <RHS, condtmp'>
166        *p = condtmp;
167
168    This transformation can only be done under several constraints,
169    documented below.  It also replaces:
170
171      bb0:
172        if (cond) goto bb2; else goto bb1;
173      bb1:
174        *p = RHS1;
175        goto bb3;
176      bb2:
177        *p = RHS2;
178      bb3:
179
180    with
181
182      bb0:
183        if (cond) goto bb3; else goto bb1;
184      bb1:
185      bb3:
186        condtmp = PHI <RHS1, RHS2>
187        *p = condtmp;  */
188
189 static unsigned int
190 tree_ssa_cs_elim (void)
191 {
192   return tree_ssa_phiopt_worker (true);
193 }
194
195 /* For conditional store replacement we need a temporary to
196    put the old contents of the memory in.  */
197 static tree condstoretemp;
198
199 /* The core routine of conditional store replacement and normal
200    phi optimizations.  Both share much of the infrastructure in how
201    to match applicable basic block patterns.  DO_STORE_ELIM is true
202    when we want to do conditional store replacement, false otherwise.  */
203 static unsigned int
204 tree_ssa_phiopt_worker (bool do_store_elim)
205 {
206   basic_block bb;
207   basic_block *bb_order;
208   unsigned n, i;
209   bool cfgchanged = false;
210   struct pointer_set_t *nontrap = 0;
211
212   if (do_store_elim)
213     {
214       condstoretemp = NULL_TREE;
215       /* Calculate the set of non-trapping memory accesses.  */
216       nontrap = get_non_trapping ();
217     }
218
219   /* Search every basic block for COND_EXPR we may be able to optimize.
220
221      We walk the blocks in order that guarantees that a block with
222      a single predecessor is processed before the predecessor.
223      This ensures that we collapse inner ifs before visiting the
224      outer ones, and also that we do not try to visit a removed
225      block.  */
226   bb_order = blocks_in_phiopt_order ();
227   n = n_basic_blocks - NUM_FIXED_BLOCKS;
228
229   for (i = 0; i < n; i++)
230     {
231       gimple cond_stmt, phi;
232       basic_block bb1, bb2;
233       edge e1, e2;
234       tree arg0, arg1;
235
236       bb = bb_order[i];
237
238       cond_stmt = last_stmt (bb);
239       /* Check to see if the last statement is a GIMPLE_COND.  */
240       if (!cond_stmt
241           || gimple_code (cond_stmt) != GIMPLE_COND)
242         continue;
243
244       e1 = EDGE_SUCC (bb, 0);
245       bb1 = e1->dest;
246       e2 = EDGE_SUCC (bb, 1);
247       bb2 = e2->dest;
248
249       /* We cannot do the optimization on abnormal edges.  */
250       if ((e1->flags & EDGE_ABNORMAL) != 0
251           || (e2->flags & EDGE_ABNORMAL) != 0)
252        continue;
253
254       /* If either bb1's succ or bb2 or bb2's succ is non NULL.  */
255       if (EDGE_COUNT (bb1->succs) == 0
256           || bb2 == NULL
257           || EDGE_COUNT (bb2->succs) == 0)
258         continue;
259
260       /* Find the bb which is the fall through to the other.  */
261       if (EDGE_SUCC (bb1, 0)->dest == bb2)
262         ;
263       else if (EDGE_SUCC (bb2, 0)->dest == bb1)
264         {
265           basic_block bb_tmp = bb1;
266           edge e_tmp = e1;
267           bb1 = bb2;
268           bb2 = bb_tmp;
269           e1 = e2;
270           e2 = e_tmp;
271         }
272       else if (do_store_elim
273                && EDGE_SUCC (bb1, 0)->dest == EDGE_SUCC (bb2, 0)->dest)
274         {
275           basic_block bb3 = EDGE_SUCC (bb1, 0)->dest;
276
277           if (!single_succ_p (bb1)
278               || (EDGE_SUCC (bb1, 0)->flags & EDGE_FALLTHRU) == 0
279               || !single_succ_p (bb2)
280               || (EDGE_SUCC (bb2, 0)->flags & EDGE_FALLTHRU) == 0
281               || EDGE_COUNT (bb3->preds) != 2)
282             continue;
283           if (cond_if_else_store_replacement (bb1, bb2, bb3))
284             cfgchanged = true;
285           continue;
286         }
287       else
288         continue;      
289
290       e1 = EDGE_SUCC (bb1, 0);
291
292       /* Make sure that bb1 is just a fall through.  */
293       if (!single_succ_p (bb1)
294           || (e1->flags & EDGE_FALLTHRU) == 0)
295         continue;
296
297       /* Also make sure that bb1 only have one predecessor and that it
298          is bb.  */
299       if (!single_pred_p (bb1)
300           || single_pred (bb1) != bb)
301         continue;
302
303       if (do_store_elim)
304         {
305           /* bb1 is the middle block, bb2 the join block, bb the split block,
306              e1 the fallthrough edge from bb1 to bb2.  We can't do the
307              optimization if the join block has more than two predecessors.  */
308           if (EDGE_COUNT (bb2->preds) > 2)
309             continue;
310           if (cond_store_replacement (bb1, bb2, e1, e2, nontrap))
311             cfgchanged = true;
312         }
313       else
314         {
315           gimple_seq phis = phi_nodes (bb2);
316           gimple_stmt_iterator gsi;
317
318           /* Check to make sure that there is only one non-virtual PHI node.
319              TODO: we could do it with more than one iff the other PHI nodes
320              have the same elements for these two edges.  */
321           phi = NULL;
322           for (gsi = gsi_start (phis); !gsi_end_p (gsi); gsi_next (&gsi))
323             {
324               if (!is_gimple_reg (gimple_phi_result (gsi_stmt (gsi))))
325                 continue;
326               if (phi)
327                 {
328                   phi = NULL;
329                   break;
330                 }
331               phi = gsi_stmt (gsi);
332             }
333           if (!phi)
334             continue;
335
336           arg0 = gimple_phi_arg_def (phi, e1->dest_idx);
337           arg1 = gimple_phi_arg_def (phi, e2->dest_idx);
338
339           /* Something is wrong if we cannot find the arguments in the PHI
340              node.  */
341           gcc_assert (arg0 != NULL && arg1 != NULL);
342
343           /* Do the replacement of conditional if it can be done.  */
344           if (conditional_replacement (bb, bb1, e1, e2, phi, arg0, arg1))
345             cfgchanged = true;
346           else if (value_replacement (bb, bb1, e1, e2, phi, arg0, arg1))
347             cfgchanged = true;
348           else if (abs_replacement (bb, bb1, e1, e2, phi, arg0, arg1))
349             cfgchanged = true;
350           else if (minmax_replacement (bb, bb1, e1, e2, phi, arg0, arg1))
351             cfgchanged = true;
352         }
353     }
354
355   free (bb_order);
356
357   if (do_store_elim)
358     pointer_set_destroy (nontrap);
359   /* If the CFG has changed, we should cleanup the CFG.  */
360   if (cfgchanged && do_store_elim)
361     {
362       /* In cond-store replacement we have added some loads on edges
363          and new VOPS (as we moved the store, and created a load).  */
364       gsi_commit_edge_inserts ();
365       return TODO_cleanup_cfg | TODO_update_ssa_only_virtuals;
366     }
367   else if (cfgchanged)
368     return TODO_cleanup_cfg;
369   return 0;
370 }
371
372 /* Returns the list of basic blocks in the function in an order that guarantees
373    that if a block X has just a single predecessor Y, then Y is after X in the
374    ordering.  */
375
376 basic_block *
377 blocks_in_phiopt_order (void)
378 {
379   basic_block x, y;
380   basic_block *order = XNEWVEC (basic_block, n_basic_blocks);
381   unsigned n = n_basic_blocks - NUM_FIXED_BLOCKS;
382   unsigned np, i;
383   sbitmap visited = sbitmap_alloc (last_basic_block);
384
385 #define MARK_VISITED(BB) (SET_BIT (visited, (BB)->index))
386 #define VISITED_P(BB) (TEST_BIT (visited, (BB)->index))
387
388   sbitmap_zero (visited);
389
390   MARK_VISITED (ENTRY_BLOCK_PTR);
391   FOR_EACH_BB (x)
392     {
393       if (VISITED_P (x))
394         continue;
395
396       /* Walk the predecessors of x as long as they have precisely one
397          predecessor and add them to the list, so that they get stored
398          after x.  */
399       for (y = x, np = 1;
400            single_pred_p (y) && !VISITED_P (single_pred (y));
401            y = single_pred (y))
402         np++;
403       for (y = x, i = n - np;
404            single_pred_p (y) && !VISITED_P (single_pred (y));
405            y = single_pred (y), i++)
406         {
407           order[i] = y;
408           MARK_VISITED (y);
409         }
410       order[i] = y;
411       MARK_VISITED (y);
412
413       gcc_assert (i == n - 1);
414       n -= np;
415     }
416
417   sbitmap_free (visited);
418   gcc_assert (n == 0);
419   return order;
420
421 #undef MARK_VISITED
422 #undef VISITED_P
423 }
424
425
426 /* Return TRUE if block BB has no executable statements, otherwise return
427    FALSE.  */
428
429 bool
430 empty_block_p (basic_block bb)
431 {
432   /* BB must have no executable statements.  */
433   gimple_stmt_iterator gsi = gsi_after_labels (bb);
434   if (gsi_end_p (gsi))
435     return true;
436   if (is_gimple_debug (gsi_stmt (gsi)))
437     gsi_next_nondebug (&gsi);
438   return gsi_end_p (gsi);
439 }
440
441 /* Replace PHI node element whose edge is E in block BB with variable NEW.
442    Remove the edge from COND_BLOCK which does not lead to BB (COND_BLOCK
443    is known to have two edges, one of which must reach BB).  */
444
445 static void
446 replace_phi_edge_with_variable (basic_block cond_block,
447                                 edge e, gimple phi, tree new_tree)
448 {
449   basic_block bb = gimple_bb (phi);
450   basic_block block_to_remove;
451   gimple_stmt_iterator gsi;
452
453   /* Change the PHI argument to new.  */
454   SET_USE (PHI_ARG_DEF_PTR (phi, e->dest_idx), new_tree);
455
456   /* Remove the empty basic block.  */
457   if (EDGE_SUCC (cond_block, 0)->dest == bb)
458     {
459       EDGE_SUCC (cond_block, 0)->flags |= EDGE_FALLTHRU;
460       EDGE_SUCC (cond_block, 0)->flags &= ~(EDGE_TRUE_VALUE | EDGE_FALSE_VALUE);
461       EDGE_SUCC (cond_block, 0)->probability = REG_BR_PROB_BASE;
462       EDGE_SUCC (cond_block, 0)->count += EDGE_SUCC (cond_block, 1)->count;
463
464       block_to_remove = EDGE_SUCC (cond_block, 1)->dest;
465     }
466   else
467     {
468       EDGE_SUCC (cond_block, 1)->flags |= EDGE_FALLTHRU;
469       EDGE_SUCC (cond_block, 1)->flags
470         &= ~(EDGE_TRUE_VALUE | EDGE_FALSE_VALUE);
471       EDGE_SUCC (cond_block, 1)->probability = REG_BR_PROB_BASE;
472       EDGE_SUCC (cond_block, 1)->count += EDGE_SUCC (cond_block, 0)->count;
473
474       block_to_remove = EDGE_SUCC (cond_block, 0)->dest;
475     }
476   delete_basic_block (block_to_remove);
477
478   /* Eliminate the COND_EXPR at the end of COND_BLOCK.  */
479   gsi = gsi_last_bb (cond_block);
480   gsi_remove (&gsi, true);
481
482   if (dump_file && (dump_flags & TDF_DETAILS))
483     fprintf (dump_file,
484               "COND_EXPR in block %d and PHI in block %d converted to straightline code.\n",
485               cond_block->index,
486               bb->index);
487 }
488
489 /*  The function conditional_replacement does the main work of doing the
490     conditional replacement.  Return true if the replacement is done.
491     Otherwise return false.
492     BB is the basic block where the replacement is going to be done on.  ARG0
493     is argument 0 from PHI.  Likewise for ARG1.  */
494
495 static bool
496 conditional_replacement (basic_block cond_bb, basic_block middle_bb,
497                          edge e0, edge e1, gimple phi,
498                          tree arg0, tree arg1)
499 {
500   tree result;
501   gimple stmt, new_stmt;
502   tree cond;
503   gimple_stmt_iterator gsi;
504   edge true_edge, false_edge;
505   tree new_var, new_var2;
506
507   /* FIXME: Gimplification of complex type is too hard for now.  */
508   if (TREE_CODE (TREE_TYPE (arg0)) == COMPLEX_TYPE
509       || TREE_CODE (TREE_TYPE (arg1)) == COMPLEX_TYPE)
510     return false;
511
512   /* The PHI arguments have the constants 0 and 1, then convert
513      it to the conditional.  */
514   if ((integer_zerop (arg0) && integer_onep (arg1))
515       || (integer_zerop (arg1) && integer_onep (arg0)))
516     ;
517   else
518     return false;
519
520   if (!empty_block_p (middle_bb))
521     return false;
522
523   /* At this point we know we have a GIMPLE_COND with two successors.
524      One successor is BB, the other successor is an empty block which
525      falls through into BB.
526
527      There is a single PHI node at the join point (BB) and its arguments
528      are constants (0, 1).
529
530      So, given the condition COND, and the two PHI arguments, we can
531      rewrite this PHI into non-branching code:
532
533        dest = (COND) or dest = COND'
534
535      We use the condition as-is if the argument associated with the
536      true edge has the value one or the argument associated with the
537      false edge as the value zero.  Note that those conditions are not
538      the same since only one of the outgoing edges from the GIMPLE_COND
539      will directly reach BB and thus be associated with an argument.  */
540
541   stmt = last_stmt (cond_bb);
542   result = PHI_RESULT (phi);
543
544   /* To handle special cases like floating point comparison, it is easier and
545      less error-prone to build a tree and gimplify it on the fly though it is
546      less efficient.  */
547   cond = fold_build2_loc (gimple_location (stmt),
548                           gimple_cond_code (stmt), boolean_type_node,
549                           gimple_cond_lhs (stmt), gimple_cond_rhs (stmt));
550
551   /* We need to know which is the true edge and which is the false
552      edge so that we know when to invert the condition below.  */
553   extract_true_false_edges_from_block (cond_bb, &true_edge, &false_edge);
554   if ((e0 == true_edge && integer_zerop (arg0))
555       || (e0 == false_edge && integer_onep (arg0))
556       || (e1 == true_edge && integer_zerop (arg1))
557       || (e1 == false_edge && integer_onep (arg1)))
558     cond = fold_build1_loc (gimple_location (stmt),
559                             TRUTH_NOT_EXPR, TREE_TYPE (cond), cond);
560
561   /* Insert our new statements at the end of conditional block before the
562      COND_STMT.  */
563   gsi = gsi_for_stmt (stmt);
564   new_var = force_gimple_operand_gsi (&gsi, cond, true, NULL, true,
565                                       GSI_SAME_STMT);
566
567   if (!useless_type_conversion_p (TREE_TYPE (result), TREE_TYPE (new_var)))
568     {
569       source_location locus_0, locus_1;
570
571       new_var2 = create_tmp_var (TREE_TYPE (result), NULL);
572       add_referenced_var (new_var2);
573       new_stmt = gimple_build_assign_with_ops (CONVERT_EXPR, new_var2,
574                                                new_var, NULL);
575       new_var2 = make_ssa_name (new_var2, new_stmt);
576       gimple_assign_set_lhs (new_stmt, new_var2);
577       gsi_insert_before (&gsi, new_stmt, GSI_SAME_STMT);
578       new_var = new_var2;
579
580       /* Set the locus to the first argument, unless is doesn't have one.  */
581       locus_0 = gimple_phi_arg_location (phi, 0);
582       locus_1 = gimple_phi_arg_location (phi, 1);
583       if (locus_0 == UNKNOWN_LOCATION)
584         locus_0 = locus_1;
585       gimple_set_location (new_stmt, locus_0);
586     }
587
588   replace_phi_edge_with_variable (cond_bb, e1, phi, new_var);
589
590   /* Note that we optimized this PHI.  */
591   return true;
592 }
593
594 /*  The function value_replacement does the main work of doing the value
595     replacement.  Return true if the replacement is done.  Otherwise return
596     false.
597     BB is the basic block where the replacement is going to be done on.  ARG0
598     is argument 0 from the PHI.  Likewise for ARG1.  */
599
600 static bool
601 value_replacement (basic_block cond_bb, basic_block middle_bb,
602                    edge e0, edge e1, gimple phi,
603                    tree arg0, tree arg1)
604 {
605   gimple cond;
606   edge true_edge, false_edge;
607   enum tree_code code;
608
609   /* If the type says honor signed zeros we cannot do this
610      optimization.  */
611   if (HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg1))))
612     return false;
613
614   if (!empty_block_p (middle_bb))
615     return false;
616
617   cond = last_stmt (cond_bb);
618   code = gimple_cond_code (cond);
619
620   /* This transformation is only valid for equality comparisons.  */
621   if (code != NE_EXPR && code != EQ_EXPR)
622     return false;
623
624   /* We need to know which is the true edge and which is the false
625       edge so that we know if have abs or negative abs.  */
626   extract_true_false_edges_from_block (cond_bb, &true_edge, &false_edge);
627
628   /* At this point we know we have a COND_EXPR with two successors.
629      One successor is BB, the other successor is an empty block which
630      falls through into BB.
631
632      The condition for the COND_EXPR is known to be NE_EXPR or EQ_EXPR.
633
634      There is a single PHI node at the join point (BB) with two arguments.
635
636      We now need to verify that the two arguments in the PHI node match
637      the two arguments to the equality comparison.  */
638
639   if ((operand_equal_for_phi_arg_p (arg0, gimple_cond_lhs (cond))
640        && operand_equal_for_phi_arg_p (arg1, gimple_cond_rhs (cond)))
641       || (operand_equal_for_phi_arg_p (arg1, gimple_cond_lhs (cond))
642           && operand_equal_for_phi_arg_p (arg0, gimple_cond_rhs (cond))))
643     {
644       edge e;
645       tree arg;
646
647       /* For NE_EXPR, we want to build an assignment result = arg where
648          arg is the PHI argument associated with the true edge.  For
649          EQ_EXPR we want the PHI argument associated with the false edge.  */
650       e = (code == NE_EXPR ? true_edge : false_edge);
651
652       /* Unfortunately, E may not reach BB (it may instead have gone to
653          OTHER_BLOCK).  If that is the case, then we want the single outgoing
654          edge from OTHER_BLOCK which reaches BB and represents the desired
655          path from COND_BLOCK.  */
656       if (e->dest == middle_bb)
657         e = single_succ_edge (e->dest);
658
659       /* Now we know the incoming edge to BB that has the argument for the
660          RHS of our new assignment statement.  */
661       if (e0 == e)
662         arg = arg0;
663       else
664         arg = arg1;
665
666       replace_phi_edge_with_variable (cond_bb, e1, phi, arg);
667
668       /* Note that we optimized this PHI.  */
669       return true;
670     }
671   return false;
672 }
673
674 /*  The function minmax_replacement does the main work of doing the minmax
675     replacement.  Return true if the replacement is done.  Otherwise return
676     false.
677     BB is the basic block where the replacement is going to be done on.  ARG0
678     is argument 0 from the PHI.  Likewise for ARG1.  */
679
680 static bool
681 minmax_replacement (basic_block cond_bb, basic_block middle_bb,
682                     edge e0, edge e1, gimple phi,
683                     tree arg0, tree arg1)
684 {
685   tree result, type;
686   gimple cond, new_stmt;
687   edge true_edge, false_edge;
688   enum tree_code cmp, minmax, ass_code;
689   tree smaller, larger, arg_true, arg_false;
690   gimple_stmt_iterator gsi, gsi_from;
691
692   type = TREE_TYPE (PHI_RESULT (phi));
693
694   /* The optimization may be unsafe due to NaNs.  */
695   if (HONOR_NANS (TYPE_MODE (type)))
696     return false;
697
698   cond = last_stmt (cond_bb);
699   cmp = gimple_cond_code (cond);
700
701   /* This transformation is only valid for order comparisons.  Record which
702      operand is smaller/larger if the result of the comparison is true.  */
703   if (cmp == LT_EXPR || cmp == LE_EXPR)
704     {
705       smaller = gimple_cond_lhs (cond);
706       larger = gimple_cond_rhs (cond);
707     }
708   else if (cmp == GT_EXPR || cmp == GE_EXPR)
709     {
710       smaller = gimple_cond_rhs (cond);
711       larger = gimple_cond_lhs (cond);
712     }
713   else
714     return false;
715
716   /* We need to know which is the true edge and which is the false
717       edge so that we know if have abs or negative abs.  */
718   extract_true_false_edges_from_block (cond_bb, &true_edge, &false_edge);
719
720   /* Forward the edges over the middle basic block.  */
721   if (true_edge->dest == middle_bb)
722     true_edge = EDGE_SUCC (true_edge->dest, 0);
723   if (false_edge->dest == middle_bb)
724     false_edge = EDGE_SUCC (false_edge->dest, 0);
725
726   if (true_edge == e0)
727     {
728       gcc_assert (false_edge == e1);
729       arg_true = arg0;
730       arg_false = arg1;
731     }
732   else
733     {
734       gcc_assert (false_edge == e0);
735       gcc_assert (true_edge == e1);
736       arg_true = arg1;
737       arg_false = arg0;
738     }
739
740   if (empty_block_p (middle_bb))
741     {
742       if (operand_equal_for_phi_arg_p (arg_true, smaller)
743           && operand_equal_for_phi_arg_p (arg_false, larger))
744         {
745           /* Case
746
747              if (smaller < larger)
748              rslt = smaller;
749              else
750              rslt = larger;  */
751           minmax = MIN_EXPR;
752         }
753       else if (operand_equal_for_phi_arg_p (arg_false, smaller)
754                && operand_equal_for_phi_arg_p (arg_true, larger))
755         minmax = MAX_EXPR;
756       else
757         return false;
758     }
759   else
760     {
761       /* Recognize the following case, assuming d <= u:
762
763          if (a <= u)
764            b = MAX (a, d);
765          x = PHI <b, u>
766
767          This is equivalent to
768
769          b = MAX (a, d);
770          x = MIN (b, u);  */
771
772       gimple assign = last_and_only_stmt (middle_bb);
773       tree lhs, op0, op1, bound;
774
775       if (!assign
776           || gimple_code (assign) != GIMPLE_ASSIGN)
777         return false;
778
779       lhs = gimple_assign_lhs (assign);
780       ass_code = gimple_assign_rhs_code (assign);
781       if (ass_code != MAX_EXPR && ass_code != MIN_EXPR)
782         return false;
783       op0 = gimple_assign_rhs1 (assign);
784       op1 = gimple_assign_rhs2 (assign);
785
786       if (true_edge->src == middle_bb)
787         {
788           /* We got here if the condition is true, i.e., SMALLER < LARGER.  */
789           if (!operand_equal_for_phi_arg_p (lhs, arg_true))
790             return false;
791
792           if (operand_equal_for_phi_arg_p (arg_false, larger))
793             {
794               /* Case
795
796                  if (smaller < larger)
797                    {
798                      r' = MAX_EXPR (smaller, bound)
799                    }
800                  r = PHI <r', larger>  --> to be turned to MIN_EXPR.  */
801               if (ass_code != MAX_EXPR)
802                 return false;
803
804               minmax = MIN_EXPR;
805               if (operand_equal_for_phi_arg_p (op0, smaller))
806                 bound = op1;
807               else if (operand_equal_for_phi_arg_p (op1, smaller))
808                 bound = op0;
809               else
810                 return false;
811
812               /* We need BOUND <= LARGER.  */
813               if (!integer_nonzerop (fold_build2 (LE_EXPR, boolean_type_node,
814                                                   bound, larger)))
815                 return false;
816             }
817           else if (operand_equal_for_phi_arg_p (arg_false, smaller))
818             {
819               /* Case
820
821                  if (smaller < larger)
822                    {
823                      r' = MIN_EXPR (larger, bound)
824                    }
825                  r = PHI <r', smaller>  --> to be turned to MAX_EXPR.  */
826               if (ass_code != MIN_EXPR)
827                 return false;
828
829               minmax = MAX_EXPR;
830               if (operand_equal_for_phi_arg_p (op0, larger))
831                 bound = op1;
832               else if (operand_equal_for_phi_arg_p (op1, larger))
833                 bound = op0;
834               else
835                 return false;
836
837               /* We need BOUND >= SMALLER.  */
838               if (!integer_nonzerop (fold_build2 (GE_EXPR, boolean_type_node,
839                                                   bound, smaller)))
840                 return false;
841             }
842           else
843             return false;
844         }
845       else
846         {
847           /* We got here if the condition is false, i.e., SMALLER > LARGER.  */
848           if (!operand_equal_for_phi_arg_p (lhs, arg_false))
849             return false;
850
851           if (operand_equal_for_phi_arg_p (arg_true, larger))
852             {
853               /* Case
854
855                  if (smaller > larger)
856                    {
857                      r' = MIN_EXPR (smaller, bound)
858                    }
859                  r = PHI <r', larger>  --> to be turned to MAX_EXPR.  */
860               if (ass_code != MIN_EXPR)
861                 return false;
862
863               minmax = MAX_EXPR;
864               if (operand_equal_for_phi_arg_p (op0, smaller))
865                 bound = op1;
866               else if (operand_equal_for_phi_arg_p (op1, smaller))
867                 bound = op0;
868               else
869                 return false;
870
871               /* We need BOUND >= LARGER.  */
872               if (!integer_nonzerop (fold_build2 (GE_EXPR, boolean_type_node,
873                                                   bound, larger)))
874                 return false;
875             }
876           else if (operand_equal_for_phi_arg_p (arg_true, smaller))
877             {
878               /* Case
879
880                  if (smaller > larger)
881                    {
882                      r' = MAX_EXPR (larger, bound)
883                    }
884                  r = PHI <r', smaller>  --> to be turned to MIN_EXPR.  */
885               if (ass_code != MAX_EXPR)
886                 return false;
887
888               minmax = MIN_EXPR;
889               if (operand_equal_for_phi_arg_p (op0, larger))
890                 bound = op1;
891               else if (operand_equal_for_phi_arg_p (op1, larger))
892                 bound = op0;
893               else
894                 return false;
895
896               /* We need BOUND <= SMALLER.  */
897               if (!integer_nonzerop (fold_build2 (LE_EXPR, boolean_type_node,
898                                                   bound, smaller)))
899                 return false;
900             }
901           else
902             return false;
903         }
904
905       /* Move the statement from the middle block.  */
906       gsi = gsi_last_bb (cond_bb);
907       gsi_from = gsi_last_nondebug_bb (middle_bb);
908       gsi_move_before (&gsi_from, &gsi);
909     }
910
911   /* Emit the statement to compute min/max.  */
912   result = duplicate_ssa_name (PHI_RESULT (phi), NULL);
913   new_stmt = gimple_build_assign_with_ops (minmax, result, arg0, arg1);
914   gsi = gsi_last_bb (cond_bb);
915   gsi_insert_before (&gsi, new_stmt, GSI_NEW_STMT);
916
917   replace_phi_edge_with_variable (cond_bb, e1, phi, result);
918   return true;
919 }
920
921 /*  The function absolute_replacement does the main work of doing the absolute
922     replacement.  Return true if the replacement is done.  Otherwise return
923     false.
924     bb is the basic block where the replacement is going to be done on.  arg0
925     is argument 0 from the phi.  Likewise for arg1.  */
926
927 static bool
928 abs_replacement (basic_block cond_bb, basic_block middle_bb,
929                  edge e0 ATTRIBUTE_UNUSED, edge e1,
930                  gimple phi, tree arg0, tree arg1)
931 {
932   tree result;
933   gimple new_stmt, cond;
934   gimple_stmt_iterator gsi;
935   edge true_edge, false_edge;
936   gimple assign;
937   edge e;
938   tree rhs, lhs;
939   bool negate;
940   enum tree_code cond_code;
941
942   /* If the type says honor signed zeros we cannot do this
943      optimization.  */
944   if (HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg1))))
945     return false;
946
947   /* OTHER_BLOCK must have only one executable statement which must have the
948      form arg0 = -arg1 or arg1 = -arg0.  */
949
950   assign = last_and_only_stmt (middle_bb);
951   /* If we did not find the proper negation assignment, then we can not
952      optimize.  */
953   if (assign == NULL)
954     return false;
955
956   /* If we got here, then we have found the only executable statement
957      in OTHER_BLOCK.  If it is anything other than arg = -arg1 or
958      arg1 = -arg0, then we can not optimize.  */
959   if (gimple_code (assign) != GIMPLE_ASSIGN)
960     return false;
961
962   lhs = gimple_assign_lhs (assign);
963
964   if (gimple_assign_rhs_code (assign) != NEGATE_EXPR)
965     return false;
966
967   rhs = gimple_assign_rhs1 (assign);
968
969   /* The assignment has to be arg0 = -arg1 or arg1 = -arg0.  */
970   if (!(lhs == arg0 && rhs == arg1)
971       && !(lhs == arg1 && rhs == arg0))
972     return false;
973
974   cond = last_stmt (cond_bb);
975   result = PHI_RESULT (phi);
976
977   /* Only relationals comparing arg[01] against zero are interesting.  */
978   cond_code = gimple_cond_code (cond);
979   if (cond_code != GT_EXPR && cond_code != GE_EXPR
980       && cond_code != LT_EXPR && cond_code != LE_EXPR)
981     return false;
982
983   /* Make sure the conditional is arg[01] OP y.  */
984   if (gimple_cond_lhs (cond) != rhs)
985     return false;
986
987   if (FLOAT_TYPE_P (TREE_TYPE (gimple_cond_rhs (cond)))
988                ? real_zerop (gimple_cond_rhs (cond))
989                : integer_zerop (gimple_cond_rhs (cond)))
990     ;
991   else
992     return false;
993
994   /* We need to know which is the true edge and which is the false
995      edge so that we know if have abs or negative abs.  */
996   extract_true_false_edges_from_block (cond_bb, &true_edge, &false_edge);
997
998   /* For GT_EXPR/GE_EXPR, if the true edge goes to OTHER_BLOCK, then we
999      will need to negate the result.  Similarly for LT_EXPR/LE_EXPR if
1000      the false edge goes to OTHER_BLOCK.  */
1001   if (cond_code == GT_EXPR || cond_code == GE_EXPR)
1002     e = true_edge;
1003   else
1004     e = false_edge;
1005
1006   if (e->dest == middle_bb)
1007     negate = true;
1008   else
1009     negate = false;
1010
1011   result = duplicate_ssa_name (result, NULL);
1012
1013   if (negate)
1014     {
1015       tree tmp = create_tmp_var (TREE_TYPE (result), NULL);
1016       add_referenced_var (tmp);
1017       lhs = make_ssa_name (tmp, NULL);
1018     }
1019   else
1020     lhs = result;
1021
1022   /* Build the modify expression with abs expression.  */
1023   new_stmt = gimple_build_assign_with_ops (ABS_EXPR, lhs, rhs, NULL);
1024
1025   gsi = gsi_last_bb (cond_bb);
1026   gsi_insert_before (&gsi, new_stmt, GSI_NEW_STMT);
1027
1028   if (negate)
1029     {
1030       /* Get the right GSI.  We want to insert after the recently
1031          added ABS_EXPR statement (which we know is the first statement
1032          in the block.  */
1033       new_stmt = gimple_build_assign_with_ops (NEGATE_EXPR, result, lhs, NULL);
1034
1035       gsi_insert_after (&gsi, new_stmt, GSI_NEW_STMT);
1036     }
1037
1038   replace_phi_edge_with_variable (cond_bb, e1, phi, result);
1039
1040   /* Note that we optimized this PHI.  */
1041   return true;
1042 }
1043
1044 /* Auxiliary functions to determine the set of memory accesses which
1045    can't trap because they are preceded by accesses to the same memory
1046    portion.  We do that for MEM_REFs, so we only need to track
1047    the SSA_NAME of the pointer indirectly referenced.  The algorithm
1048    simply is a walk over all instructions in dominator order.  When
1049    we see an MEM_REF we determine if we've already seen a same
1050    ref anywhere up to the root of the dominator tree.  If we do the
1051    current access can't trap.  If we don't see any dominating access
1052    the current access might trap, but might also make later accesses
1053    non-trapping, so we remember it.  We need to be careful with loads
1054    or stores, for instance a load might not trap, while a store would,
1055    so if we see a dominating read access this doesn't mean that a later
1056    write access would not trap.  Hence we also need to differentiate the
1057    type of access(es) seen.
1058
1059    ??? We currently are very conservative and assume that a load might
1060    trap even if a store doesn't (write-only memory).  This probably is
1061    overly conservative.  */
1062
1063 /* A hash-table of SSA_NAMEs, and in which basic block an MEM_REF
1064    through it was seen, which would constitute a no-trap region for
1065    same accesses.  */
1066 struct name_to_bb
1067 {
1068   tree ssa_name;
1069   basic_block bb;
1070   unsigned store : 1;
1071 };
1072
1073 /* The hash table for remembering what we've seen.  */
1074 static htab_t seen_ssa_names;
1075
1076 /* The set of MEM_REFs which can't trap.  */
1077 static struct pointer_set_t *nontrap_set;
1078
1079 /* The hash function, based on the pointer to the pointer SSA_NAME.  */
1080 static hashval_t
1081 name_to_bb_hash (const void *p)
1082 {
1083   const_tree n = ((const struct name_to_bb *)p)->ssa_name;
1084   return htab_hash_pointer (n) ^ ((const struct name_to_bb *)p)->store;
1085 }
1086
1087 /* The equality function of *P1 and *P2.  SSA_NAMEs are shared, so
1088    it's enough to simply compare them for equality.  */
1089 static int
1090 name_to_bb_eq (const void *p1, const void *p2)
1091 {
1092   const struct name_to_bb *n1 = (const struct name_to_bb *)p1;
1093   const struct name_to_bb *n2 = (const struct name_to_bb *)p2;
1094
1095   return n1->ssa_name == n2->ssa_name && n1->store == n2->store;
1096 }
1097
1098 /* We see the expression EXP in basic block BB.  If it's an interesting
1099    expression (an MEM_REF through an SSA_NAME) possibly insert the
1100    expression into the set NONTRAP or the hash table of seen expressions.
1101    STORE is true if this expression is on the LHS, otherwise it's on
1102    the RHS.  */
1103 static void
1104 add_or_mark_expr (basic_block bb, tree exp,
1105                   struct pointer_set_t *nontrap, bool store)
1106 {
1107   if (TREE_CODE (exp) == MEM_REF
1108       && TREE_CODE (TREE_OPERAND (exp, 0)) == SSA_NAME)
1109     {
1110       tree name = TREE_OPERAND (exp, 0);
1111       struct name_to_bb map;
1112       void **slot;
1113       struct name_to_bb *n2bb;
1114       basic_block found_bb = 0;
1115
1116       /* Try to find the last seen MEM_REF through the same
1117          SSA_NAME, which can trap.  */
1118       map.ssa_name = name;
1119       map.bb = 0;
1120       map.store = store;
1121       slot = htab_find_slot (seen_ssa_names, &map, INSERT);
1122       n2bb = (struct name_to_bb *) *slot;
1123       if (n2bb)
1124         found_bb = n2bb->bb;
1125
1126       /* If we've found a trapping MEM_REF, _and_ it dominates EXP
1127          (it's in a basic block on the path from us to the dominator root)
1128          then we can't trap.  */
1129       if (found_bb && found_bb->aux == (void *)1)
1130         {
1131           pointer_set_insert (nontrap, exp);
1132         }
1133       else
1134         {
1135           /* EXP might trap, so insert it into the hash table.  */
1136           if (n2bb)
1137             {
1138               n2bb->bb = bb;
1139             }
1140           else
1141             {
1142               n2bb = XNEW (struct name_to_bb);
1143               n2bb->ssa_name = name;
1144               n2bb->bb = bb;
1145               n2bb->store = store;
1146               *slot = n2bb;
1147             }
1148         }
1149     }
1150 }
1151
1152 /* Called by walk_dominator_tree, when entering the block BB.  */
1153 static void
1154 nt_init_block (struct dom_walk_data *data ATTRIBUTE_UNUSED, basic_block bb)
1155 {
1156   gimple_stmt_iterator gsi;
1157   /* Mark this BB as being on the path to dominator root.  */
1158   bb->aux = (void*)1;
1159
1160   /* And walk the statements in order.  */
1161   for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
1162     {
1163       gimple stmt = gsi_stmt (gsi);
1164
1165       if (is_gimple_assign (stmt))
1166         {
1167           add_or_mark_expr (bb, gimple_assign_lhs (stmt), nontrap_set, true);
1168           add_or_mark_expr (bb, gimple_assign_rhs1 (stmt), nontrap_set, false);
1169           if (get_gimple_rhs_num_ops (gimple_assign_rhs_code (stmt)) > 1)
1170             add_or_mark_expr (bb, gimple_assign_rhs2 (stmt), nontrap_set,
1171                               false);
1172         }
1173     }
1174 }
1175
1176 /* Called by walk_dominator_tree, when basic block BB is exited.  */
1177 static void
1178 nt_fini_block (struct dom_walk_data *data ATTRIBUTE_UNUSED, basic_block bb)
1179 {
1180   /* This BB isn't on the path to dominator root anymore.  */
1181   bb->aux = NULL;
1182 }
1183
1184 /* This is the entry point of gathering non trapping memory accesses.
1185    It will do a dominator walk over the whole function, and it will
1186    make use of the bb->aux pointers.  It returns a set of trees
1187    (the MEM_REFs itself) which can't trap.  */
1188 static struct pointer_set_t *
1189 get_non_trapping (void)
1190 {
1191   struct pointer_set_t *nontrap;
1192   struct dom_walk_data walk_data;
1193
1194   nontrap = pointer_set_create ();
1195   seen_ssa_names = htab_create (128, name_to_bb_hash, name_to_bb_eq,
1196                                 free);
1197   /* We're going to do a dominator walk, so ensure that we have
1198      dominance information.  */
1199   calculate_dominance_info (CDI_DOMINATORS);
1200
1201   /* Setup callbacks for the generic dominator tree walker.  */
1202   nontrap_set = nontrap;
1203   walk_data.dom_direction = CDI_DOMINATORS;
1204   walk_data.initialize_block_local_data = NULL;
1205   walk_data.before_dom_children = nt_init_block;
1206   walk_data.after_dom_children = nt_fini_block;
1207   walk_data.global_data = NULL;
1208   walk_data.block_local_data_size = 0;
1209
1210   init_walk_dominator_tree (&walk_data);
1211   walk_dominator_tree (&walk_data, ENTRY_BLOCK_PTR);
1212   fini_walk_dominator_tree (&walk_data);
1213   htab_delete (seen_ssa_names);
1214
1215   return nontrap;
1216 }
1217
1218 /* Do the main work of conditional store replacement.  We already know
1219    that the recognized pattern looks like so:
1220
1221    split:
1222      if (cond) goto MIDDLE_BB; else goto JOIN_BB (edge E1)
1223    MIDDLE_BB:
1224      something
1225      fallthrough (edge E0)
1226    JOIN_BB:
1227      some more
1228
1229    We check that MIDDLE_BB contains only one store, that that store
1230    doesn't trap (not via NOTRAP, but via checking if an access to the same
1231    memory location dominates us) and that the store has a "simple" RHS.  */
1232
1233 static bool
1234 cond_store_replacement (basic_block middle_bb, basic_block join_bb,
1235                         edge e0, edge e1, struct pointer_set_t *nontrap)
1236 {
1237   gimple assign = last_and_only_stmt (middle_bb);
1238   tree lhs, rhs, name;
1239   gimple newphi, new_stmt;
1240   gimple_stmt_iterator gsi;
1241   source_location locus;
1242
1243   /* Check if middle_bb contains of only one store.  */
1244   if (!assign
1245       || !gimple_assign_single_p (assign))
1246     return false;
1247
1248   locus = gimple_location (assign);
1249   lhs = gimple_assign_lhs (assign);
1250   rhs = gimple_assign_rhs1 (assign);
1251   if (TREE_CODE (lhs) != MEM_REF
1252       || TREE_CODE (TREE_OPERAND (lhs, 0)) != SSA_NAME
1253       || !is_gimple_reg_type (TREE_TYPE (lhs)))
1254     return false;
1255
1256   /* Prove that we can move the store down.  We could also check
1257      TREE_THIS_NOTRAP here, but in that case we also could move stores,
1258      whose value is not available readily, which we want to avoid.  */
1259   if (!pointer_set_contains (nontrap, lhs))
1260     return false;
1261
1262   /* Now we've checked the constraints, so do the transformation:
1263      1) Remove the single store.  */
1264   gsi = gsi_for_stmt (assign);
1265   unlink_stmt_vdef (assign);
1266   gsi_remove (&gsi, true);
1267   release_defs (assign);
1268
1269   /* 2) Create a temporary where we can store the old content
1270         of the memory touched by the store, if we need to.  */
1271   if (!condstoretemp || TREE_TYPE (lhs) != TREE_TYPE (condstoretemp))
1272     condstoretemp = create_tmp_reg (TREE_TYPE (lhs), "cstore");
1273   add_referenced_var (condstoretemp);
1274
1275   /* 3) Insert a load from the memory of the store to the temporary
1276         on the edge which did not contain the store.  */
1277   lhs = unshare_expr (lhs);
1278   new_stmt = gimple_build_assign (condstoretemp, lhs);
1279   name = make_ssa_name (condstoretemp, new_stmt);
1280   gimple_assign_set_lhs (new_stmt, name);
1281   gimple_set_location (new_stmt, locus);
1282   gsi_insert_on_edge (e1, new_stmt);
1283
1284   /* 4) Create a PHI node at the join block, with one argument
1285         holding the old RHS, and the other holding the temporary
1286         where we stored the old memory contents.  */
1287   newphi = create_phi_node (condstoretemp, join_bb);
1288   add_phi_arg (newphi, rhs, e0, locus);
1289   add_phi_arg (newphi, name, e1, locus);
1290
1291   lhs = unshare_expr (lhs);
1292   new_stmt = gimple_build_assign (lhs, PHI_RESULT (newphi));
1293
1294   /* 5) Insert that PHI node.  */
1295   gsi = gsi_after_labels (join_bb);
1296   if (gsi_end_p (gsi))
1297     {
1298       gsi = gsi_last_bb (join_bb);
1299       gsi_insert_after (&gsi, new_stmt, GSI_NEW_STMT);
1300     }
1301   else
1302     gsi_insert_before (&gsi, new_stmt, GSI_NEW_STMT);
1303
1304   return true;
1305 }
1306
1307 /* Do the main work of conditional store replacement.  */
1308
1309 static bool
1310 cond_if_else_store_replacement_1 (basic_block then_bb, basic_block else_bb,
1311                                   basic_block join_bb, gimple then_assign,
1312                                   gimple else_assign)
1313 {
1314   tree lhs_base, lhs, then_rhs, else_rhs;
1315   source_location then_locus, else_locus;
1316   gimple_stmt_iterator gsi;
1317   gimple newphi, new_stmt;
1318
1319   if (then_assign == NULL
1320       || !gimple_assign_single_p (then_assign)
1321       || else_assign == NULL
1322       || !gimple_assign_single_p (else_assign))
1323     return false;
1324
1325   lhs = gimple_assign_lhs (then_assign);
1326   if (!is_gimple_reg_type (TREE_TYPE (lhs))
1327       || !operand_equal_p (lhs, gimple_assign_lhs (else_assign), 0))
1328     return false;
1329
1330   lhs_base = get_base_address (lhs);
1331   if (lhs_base == NULL_TREE
1332       || (!DECL_P (lhs_base) && TREE_CODE (lhs_base) != MEM_REF))
1333     return false;
1334
1335   then_rhs = gimple_assign_rhs1 (then_assign);
1336   else_rhs = gimple_assign_rhs1 (else_assign);
1337   then_locus = gimple_location (then_assign);
1338   else_locus = gimple_location (else_assign);
1339
1340   /* Now we've checked the constraints, so do the transformation:
1341      1) Remove the stores.  */
1342   gsi = gsi_for_stmt (then_assign);
1343   unlink_stmt_vdef (then_assign);
1344   gsi_remove (&gsi, true);
1345   release_defs (then_assign);
1346
1347   gsi = gsi_for_stmt (else_assign);
1348   unlink_stmt_vdef (else_assign);
1349   gsi_remove (&gsi, true);
1350   release_defs (else_assign);
1351
1352   /* 2) Create a temporary where we can store the old content
1353         of the memory touched by the store, if we need to.  */
1354   if (!condstoretemp || TREE_TYPE (lhs) != TREE_TYPE (condstoretemp))
1355     condstoretemp = create_tmp_reg (TREE_TYPE (lhs), "cstore");
1356   add_referenced_var (condstoretemp);
1357
1358   /* 3) Create a PHI node at the join block, with one argument
1359         holding the old RHS, and the other holding the temporary
1360         where we stored the old memory contents.  */
1361   newphi = create_phi_node (condstoretemp, join_bb);
1362   add_phi_arg (newphi, then_rhs, EDGE_SUCC (then_bb, 0), then_locus);
1363   add_phi_arg (newphi, else_rhs, EDGE_SUCC (else_bb, 0), else_locus);
1364
1365   new_stmt = gimple_build_assign (lhs, PHI_RESULT (newphi));
1366
1367   /* 4) Insert that PHI node.  */
1368   gsi = gsi_after_labels (join_bb);
1369   if (gsi_end_p (gsi))
1370     {
1371       gsi = gsi_last_bb (join_bb);
1372       gsi_insert_after (&gsi, new_stmt, GSI_NEW_STMT);
1373     }
1374   else
1375     gsi_insert_before (&gsi, new_stmt, GSI_NEW_STMT);
1376
1377   return true;
1378 }
1379
1380 /* Conditional store replacement.  We already know
1381    that the recognized pattern looks like so:
1382
1383    split:
1384      if (cond) goto THEN_BB; else goto ELSE_BB (edge E1)
1385    THEN_BB:
1386      ...
1387      X = Y;
1388      ...
1389      goto JOIN_BB;
1390    ELSE_BB:
1391      ...
1392      X = Z;
1393      ...
1394      fallthrough (edge E0)
1395    JOIN_BB:
1396      some more
1397
1398    We check that it is safe to sink the store to JOIN_BB by verifying that
1399    there are no read-after-write or write-after-write dependencies in
1400    THEN_BB and ELSE_BB.  */
1401
1402 static bool
1403 cond_if_else_store_replacement (basic_block then_bb, basic_block else_bb,
1404                                 basic_block join_bb)
1405 {
1406   gimple then_assign = last_and_only_stmt (then_bb);
1407   gimple else_assign = last_and_only_stmt (else_bb);
1408   VEC (data_reference_p, heap) *then_datarefs, *else_datarefs;
1409   VEC (ddr_p, heap) *then_ddrs, *else_ddrs;
1410   gimple then_store, else_store;
1411   bool found, ok = false, res;
1412   struct data_dependence_relation *ddr;
1413   data_reference_p then_dr, else_dr;
1414   int i, j;
1415   tree then_lhs, else_lhs;
1416   VEC (gimple, heap) *then_stores, *else_stores;
1417   basic_block blocks[3];
1418
1419   if (MAX_STORES_TO_SINK == 0)
1420     return false;
1421
1422   /* Handle the case with single statement in THEN_BB and ELSE_BB.  */
1423   if (then_assign && else_assign)
1424     return cond_if_else_store_replacement_1 (then_bb, else_bb, join_bb,
1425                                              then_assign, else_assign);
1426
1427   /* Find data references.  */
1428   then_datarefs = VEC_alloc (data_reference_p, heap, 1);
1429   else_datarefs = VEC_alloc (data_reference_p, heap, 1);
1430   if ((find_data_references_in_bb (NULL, then_bb, &then_datarefs)
1431         == chrec_dont_know)
1432       || !VEC_length (data_reference_p, then_datarefs)
1433       || (find_data_references_in_bb (NULL, else_bb, &else_datarefs)
1434         == chrec_dont_know)
1435       || !VEC_length (data_reference_p, else_datarefs))
1436     {
1437       free_data_refs (then_datarefs);
1438       free_data_refs (else_datarefs);
1439       return false;
1440     }
1441
1442   /* Find pairs of stores with equal LHS.  */
1443   then_stores = VEC_alloc (gimple, heap, 1);
1444   else_stores = VEC_alloc (gimple, heap, 1);
1445   FOR_EACH_VEC_ELT (data_reference_p, then_datarefs, i, then_dr)
1446     {
1447       if (DR_IS_READ (then_dr))
1448         continue;
1449
1450       then_store = DR_STMT (then_dr);
1451       then_lhs = gimple_get_lhs (then_store);
1452       found = false;
1453
1454       FOR_EACH_VEC_ELT (data_reference_p, else_datarefs, j, else_dr)
1455         {
1456           if (DR_IS_READ (else_dr))
1457             continue;
1458
1459           else_store = DR_STMT (else_dr);
1460           else_lhs = gimple_get_lhs (else_store);
1461
1462           if (operand_equal_p (then_lhs, else_lhs, 0))
1463             {
1464               found = true;
1465               break;
1466             }
1467         }
1468
1469       if (!found)
1470         continue;
1471
1472       VEC_safe_push (gimple, heap, then_stores, then_store);
1473       VEC_safe_push (gimple, heap, else_stores, else_store);
1474     }
1475
1476   /* No pairs of stores found.  */
1477   if (!VEC_length (gimple, then_stores)
1478       || VEC_length (gimple, then_stores) > (unsigned) MAX_STORES_TO_SINK)
1479     {
1480       free_data_refs (then_datarefs);
1481       free_data_refs (else_datarefs);
1482       VEC_free (gimple, heap, then_stores);
1483       VEC_free (gimple, heap, else_stores);
1484       return false;
1485     }
1486
1487   /* Compute and check data dependencies in both basic blocks.  */
1488   then_ddrs = VEC_alloc (ddr_p, heap, 1);
1489   else_ddrs = VEC_alloc (ddr_p, heap, 1);
1490   compute_all_dependences (then_datarefs, &then_ddrs, NULL, false);
1491   compute_all_dependences (else_datarefs, &else_ddrs, NULL, false);
1492   blocks[0] = then_bb;
1493   blocks[1] = else_bb;
1494   blocks[2] = join_bb;
1495   renumber_gimple_stmt_uids_in_blocks (blocks, 3);
1496
1497   /* Check that there are no read-after-write or write-after-write dependencies
1498      in THEN_BB.  */
1499   FOR_EACH_VEC_ELT (ddr_p, then_ddrs, i, ddr)
1500     {
1501       struct data_reference *dra = DDR_A (ddr);
1502       struct data_reference *drb = DDR_B (ddr);
1503
1504       if (DDR_ARE_DEPENDENT (ddr) != chrec_known
1505           && ((DR_IS_READ (dra) && DR_IS_WRITE (drb)
1506                && gimple_uid (DR_STMT (dra)) > gimple_uid (DR_STMT (drb)))
1507               || (DR_IS_READ (drb) && DR_IS_WRITE (dra)
1508                   && gimple_uid (DR_STMT (drb)) > gimple_uid (DR_STMT (dra)))
1509               || (DR_IS_WRITE (dra) && DR_IS_WRITE (drb))))
1510         {
1511           free_dependence_relations (then_ddrs);
1512           free_dependence_relations (else_ddrs);
1513           free_data_refs (then_datarefs);
1514           free_data_refs (else_datarefs);
1515           VEC_free (gimple, heap, then_stores);
1516           VEC_free (gimple, heap, else_stores);
1517           return false;
1518         }
1519     }
1520
1521   /* Check that there are no read-after-write or write-after-write dependencies
1522      in ELSE_BB.  */
1523   FOR_EACH_VEC_ELT (ddr_p, else_ddrs, i, ddr)
1524     {
1525       struct data_reference *dra = DDR_A (ddr);
1526       struct data_reference *drb = DDR_B (ddr);
1527
1528       if (DDR_ARE_DEPENDENT (ddr) != chrec_known
1529           && ((DR_IS_READ (dra) && DR_IS_WRITE (drb)
1530                && gimple_uid (DR_STMT (dra)) > gimple_uid (DR_STMT (drb)))
1531               || (DR_IS_READ (drb) && DR_IS_WRITE (dra)
1532                   && gimple_uid (DR_STMT (drb)) > gimple_uid (DR_STMT (dra)))
1533               || (DR_IS_WRITE (dra) && DR_IS_WRITE (drb))))
1534         {
1535           free_dependence_relations (then_ddrs);
1536           free_dependence_relations (else_ddrs);
1537           free_data_refs (then_datarefs);
1538           free_data_refs (else_datarefs);
1539           VEC_free (gimple, heap, then_stores);
1540           VEC_free (gimple, heap, else_stores);
1541           return false;
1542         }
1543     }
1544
1545   /* Sink stores with same LHS.  */
1546   FOR_EACH_VEC_ELT (gimple, then_stores, i, then_store)
1547     {
1548       else_store = VEC_index (gimple, else_stores, i);
1549       res = cond_if_else_store_replacement_1 (then_bb, else_bb, join_bb,
1550                                               then_store, else_store);
1551       ok = ok || res;
1552     }
1553
1554   free_dependence_relations (then_ddrs);
1555   free_dependence_relations (else_ddrs);
1556   free_data_refs (then_datarefs);
1557   free_data_refs (else_datarefs);
1558   VEC_free (gimple, heap, then_stores);
1559   VEC_free (gimple, heap, else_stores);
1560
1561   return ok;
1562 }
1563
1564 /* Always do these optimizations if we have SSA
1565    trees to work on.  */
1566 static bool
1567 gate_phiopt (void)
1568 {
1569   return 1;
1570 }
1571
1572 struct gimple_opt_pass pass_phiopt =
1573 {
1574  {
1575   GIMPLE_PASS,
1576   "phiopt",                             /* name */
1577   gate_phiopt,                          /* gate */
1578   tree_ssa_phiopt,                      /* execute */
1579   NULL,                                 /* sub */
1580   NULL,                                 /* next */
1581   0,                                    /* static_pass_number */
1582   TV_TREE_PHIOPT,                       /* tv_id */
1583   PROP_cfg | PROP_ssa,                  /* properties_required */
1584   0,                                    /* properties_provided */
1585   0,                                    /* properties_destroyed */
1586   0,                                    /* todo_flags_start */
1587   TODO_ggc_collect
1588     | TODO_verify_ssa
1589     | TODO_verify_flow
1590     | TODO_verify_stmts                 /* todo_flags_finish */
1591  }
1592 };
1593
1594 static bool
1595 gate_cselim (void)
1596 {
1597   return flag_tree_cselim;
1598 }
1599
1600 struct gimple_opt_pass pass_cselim =
1601 {
1602  {
1603   GIMPLE_PASS,
1604   "cselim",                             /* name */
1605   gate_cselim,                          /* gate */
1606   tree_ssa_cs_elim,                     /* execute */
1607   NULL,                                 /* sub */
1608   NULL,                                 /* next */
1609   0,                                    /* static_pass_number */
1610   TV_TREE_PHIOPT,                       /* tv_id */
1611   PROP_cfg | PROP_ssa,                  /* properties_required */
1612   0,                                    /* properties_provided */
1613   0,                                    /* properties_destroyed */
1614   0,                                    /* todo_flags_start */
1615   TODO_ggc_collect
1616     | TODO_verify_ssa
1617     | TODO_verify_flow
1618     | TODO_verify_stmts                 /* todo_flags_finish */
1619  }
1620 };