1 /* Optimization of PHI nodes by converting them into straightline code.
2 Copyright (C) 2004, 2005 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify it
7 under the terms of the GNU General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
11 GCC is distributed in the hope that it will be useful, but WITHOUT
12 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING. If not, write to the Free
18 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
23 #include "coretypes.h"
31 #include "basic-block.h"
33 #include "diagnostic.h"
34 #include "tree-flow.h"
35 #include "tree-pass.h"
36 #include "tree-dump.h"
37 #include "langhooks.h"
39 static void tree_ssa_phiopt (void);
40 static bool conditional_replacement (basic_block
, basic_block
, basic_block
,
41 edge
, edge
, tree
, tree
, tree
);
42 static bool value_replacement (basic_block
, basic_block
, basic_block
,
43 edge
, edge
, tree
, tree
, tree
);
44 static bool minmax_replacement (basic_block
, basic_block
, basic_block
,
45 edge
, edge
, tree
, tree
, tree
);
46 static bool abs_replacement (basic_block
, basic_block
, basic_block
,
47 edge
, edge
, tree
, tree
, tree
);
48 static void replace_phi_edge_with_variable (basic_block
, basic_block
, edge
,
50 static basic_block
*blocks_in_phiopt_order (void);
52 /* This pass eliminates PHI nodes which can be trivially implemented as
53 an assignment from a conditional expression. i.e. if we have something
57 if (cond) goto bb2; else goto bb1;
60 x = PHI (0 (bb1), 1 (bb0)
62 We can rewrite that as:
69 bb1 will become unreachable and bb0 and bb2 will almost always
70 be merged into a single block. This occurs often due to gimplification
73 Also done is the following optimization:
76 if (a != b) goto bb2; else goto bb1;
79 x = PHI (a (bb1), b (bb0))
81 We can rewrite that as:
88 This can sometimes occur as a result of other optimizations. A
89 similar transformation is done by the ifcvt RTL optimizer.
91 This pass also eliminates PHI nodes which are really absolute
92 values. i.e. if we have something like:
95 if (a >= 0) goto bb2; else goto bb1;
99 x = PHI (x (bb1), a (bb0));
101 We can rewrite that as:
111 if (a <= b) goto bb2; else goto bb1;
115 x = PHI (b (bb1), a (bb0));
121 And the same transformation for MAX_EXPR.
123 bb1 will become unreachable and bb0 and bb2 will almost always be merged
124 into a single block. Similar transformations are done by the ifcvt
128 tree_ssa_phiopt (void)
131 basic_block
*bb_order
;
134 /* Search every basic block for COND_EXPR we may be able to optimize.
136 We walk the blocks in order that guarantees that a block with
137 a single predecessor is processed before the predecessor.
138 This ensures that we collapse inner ifs before visiting the
139 outer ones, and also that we do not try to visit a removed
141 bb_order
= blocks_in_phiopt_order ();
144 for (i
= 0; i
< n
; i
++)
148 basic_block bb1
, bb2
;
154 cond_expr
= last_stmt (bb
);
155 /* Check to see if the last statement is a COND_EXPR. */
157 || TREE_CODE (cond_expr
) != COND_EXPR
)
160 e1
= EDGE_SUCC (bb
, 0);
162 e2
= EDGE_SUCC (bb
, 1);
165 /* We cannot do the optimization on abnormal edges. */
166 if ((e1
->flags
& EDGE_ABNORMAL
) != 0
167 || (e2
->flags
& EDGE_ABNORMAL
) != 0)
170 /* If either bb1's succ or bb2 or bb2's succ is non NULL. */
171 if (EDGE_COUNT (bb1
->succs
) == 0
173 || EDGE_COUNT (bb2
->succs
) == 0)
176 /* Find the bb which is the fall through to the other. */
177 if (EDGE_SUCC (bb1
, 0)->dest
== bb2
)
179 else if (EDGE_SUCC (bb2
, 0)->dest
== bb1
)
181 basic_block bb_tmp
= bb1
;
191 e1
= EDGE_SUCC (bb1
, 0);
193 /* Make sure that bb1 is just a fall through. */
194 if (!single_succ_p (bb1
) > 1
195 || (e1
->flags
& EDGE_FALLTHRU
) == 0)
198 /* Also make that bb1 only have one pred and it is bb. */
199 if (!single_pred_p (bb1
)
200 || single_pred (bb1
) != bb
)
203 phi
= phi_nodes (bb2
);
205 /* Check to make sure that there is only one PHI node.
206 TODO: we could do it with more than one iff the other PHI nodes
207 have the same elements for these two edges. */
208 if (!phi
|| PHI_CHAIN (phi
) != NULL
)
211 arg0
= PHI_ARG_DEF_TREE (phi
, e1
->dest_idx
);
212 arg1
= PHI_ARG_DEF_TREE (phi
, e2
->dest_idx
);
214 /* We know something is wrong if we cannot find the edges in the PHI
216 gcc_assert (arg0
!= NULL
&& arg1
!= NULL
);
218 /* Do the replacement of conditional if it can be done. */
219 if (conditional_replacement (bb
, bb1
, bb2
, e1
, e2
, phi
, arg0
, arg1
))
221 else if (value_replacement (bb
, bb1
, bb2
, e1
, e2
, phi
, arg0
, arg1
))
223 else if (abs_replacement (bb
, bb1
, bb2
, e1
, e2
, phi
, arg0
, arg1
))
226 minmax_replacement (bb
, bb1
, bb2
, e1
, e2
, phi
, arg0
, arg1
);
232 /* Returns the list of basic blocks in the function in an order that guarantees
233 that if a block X has just a single predecessor Y, then Y is after X in the
237 blocks_in_phiopt_order (void)
240 basic_block
*order
= xmalloc (sizeof (basic_block
) * n_basic_blocks
);
241 unsigned n
= n_basic_blocks
, np
, i
;
242 sbitmap visited
= sbitmap_alloc (last_basic_block
+ 2);
244 #define MARK_VISITED(BB) (SET_BIT (visited, (BB)->index + 2))
245 #define VISITED_P(BB) (TEST_BIT (visited, (BB)->index + 2))
247 sbitmap_zero (visited
);
249 MARK_VISITED (ENTRY_BLOCK_PTR
);
255 /* Walk the predecessors of x as long as they have precisely one
256 predecessor and add them to the list, so that they get stored
259 single_pred_p (y
) && !VISITED_P (single_pred (y
));
262 for (y
= x
, i
= n
- np
;
263 single_pred_p (y
) && !VISITED_P (single_pred (y
));
264 y
= single_pred (y
), i
++)
272 gcc_assert (i
== n
- 1);
276 sbitmap_free (visited
);
284 /* Return TRUE if block BB has no executable statements, otherwise return
287 empty_block_p (basic_block bb
)
289 block_stmt_iterator bsi
;
291 /* BB must have no executable statements. */
292 bsi
= bsi_start (bb
);
293 while (!bsi_end_p (bsi
)
294 && (TREE_CODE (bsi_stmt (bsi
)) == LABEL_EXPR
295 || IS_EMPTY_STMT (bsi_stmt (bsi
))))
298 if (!bsi_end_p (bsi
))
304 /* Replace PHI node element whoes edge is E in block BB with variable NEW.
305 Remove the edge from COND_BLOCK which does not lead to BB (COND_BLOCK
306 is known to have two edges, one of which must reach BB). */
309 replace_phi_edge_with_variable (basic_block cond_block
, basic_block bb
,
310 edge e
, tree phi
, tree
new)
312 basic_block block_to_remove
;
313 block_stmt_iterator bsi
;
315 /* Change the PHI argument to new. */
316 SET_USE (PHI_ARG_DEF_PTR (phi
, e
->dest_idx
), new);
318 /* Remove the empty basic block. */
319 if (EDGE_SUCC (cond_block
, 0)->dest
== bb
)
321 EDGE_SUCC (cond_block
, 0)->flags
|= EDGE_FALLTHRU
;
322 EDGE_SUCC (cond_block
, 0)->flags
&= ~(EDGE_TRUE_VALUE
| EDGE_FALSE_VALUE
);
324 block_to_remove
= EDGE_SUCC (cond_block
, 1)->dest
;
328 EDGE_SUCC (cond_block
, 1)->flags
|= EDGE_FALLTHRU
;
329 EDGE_SUCC (cond_block
, 1)->flags
330 &= ~(EDGE_TRUE_VALUE
| EDGE_FALSE_VALUE
);
332 block_to_remove
= EDGE_SUCC (cond_block
, 0)->dest
;
334 delete_basic_block (block_to_remove
);
336 /* Eliminate the COND_EXPR at the end of COND_BLOCK. */
337 bsi
= bsi_last (cond_block
);
340 if (dump_file
&& (dump_flags
& TDF_DETAILS
))
342 "COND_EXPR in block %d and PHI in block %d converted to straightline code.\n",
347 /* The function conditional_replacement does the main work of doing the
348 conditional replacement. Return true if the replacement is done.
349 Otherwise return false.
350 BB is the basic block where the replacement is going to be done on. ARG0
351 is argument 0 from PHI. Likewise for ARG1. */
354 conditional_replacement (basic_block cond_bb
, basic_block middle_bb
,
355 basic_block phi_bb
, edge e0
, edge e1
, tree phi
,
356 tree arg0
, tree arg1
)
359 tree old_result
= NULL
;
361 block_stmt_iterator bsi
;
362 edge true_edge
, false_edge
;
366 /* The PHI arguments have the constants 0 and 1, then convert
367 it to the conditional. */
368 if ((integer_zerop (arg0
) && integer_onep (arg1
))
369 || (integer_zerop (arg1
) && integer_onep (arg0
)))
374 if (!empty_block_p (middle_bb
))
377 /* If the condition is not a naked SSA_NAME and its type does not
378 match the type of the result, then we have to create a new
379 variable to optimize this case as it would likely create
380 non-gimple code when the condition was converted to the
382 cond
= COND_EXPR_COND (last_stmt (cond_bb
));
383 result
= PHI_RESULT (phi
);
384 if (TREE_CODE (cond
) != SSA_NAME
385 && !lang_hooks
.types_compatible_p (TREE_TYPE (cond
), TREE_TYPE (result
)))
387 new_var
= make_rename_temp (TREE_TYPE (cond
), NULL
);
392 /* If the condition was a naked SSA_NAME and the type is not the
393 same as the type of the result, then convert the type of the
395 if (!lang_hooks
.types_compatible_p (TREE_TYPE (cond
), TREE_TYPE (result
)))
396 cond
= fold_convert (TREE_TYPE (result
), cond
);
398 /* We need to know which is the true edge and which is the false
399 edge so that we know when to invert the condition below. */
400 extract_true_false_edges_from_block (cond_bb
, &true_edge
, &false_edge
);
402 /* Insert our new statement at the end of conditional block before the
404 bsi
= bsi_last (cond_bb
);
405 bsi_insert_before (&bsi
, build_empty_stmt (), BSI_NEW_STMT
);
410 if (!COMPARISON_CLASS_P (old_result
))
413 new1
= build2 (TREE_CODE (old_result
), TREE_TYPE (old_result
),
414 TREE_OPERAND (old_result
, 0),
415 TREE_OPERAND (old_result
, 1));
417 new1
= build2 (MODIFY_EXPR
, TREE_TYPE (old_result
), new_var
, new1
);
418 bsi_insert_after (&bsi
, new1
, BSI_NEW_STMT
);
421 new_var1
= duplicate_ssa_name (PHI_RESULT (phi
), NULL
);
424 /* At this point we know we have a COND_EXPR with two successors.
425 One successor is BB, the other successor is an empty block which
426 falls through into BB.
428 There is a single PHI node at the join point (BB) and its arguments
429 are constants (0, 1).
431 So, given the condition COND, and the two PHI arguments, we can
432 rewrite this PHI into non-branching code:
434 dest = (COND) or dest = COND'
436 We use the condition as-is if the argument associated with the
437 true edge has the value one or the argument associated with the
438 false edge as the value zero. Note that those conditions are not
439 the same since only one of the outgoing edges from the COND_EXPR
440 will directly reach BB and thus be associated with an argument. */
441 if ((e0
== true_edge
&& integer_onep (arg0
))
442 || (e0
== false_edge
&& integer_zerop (arg0
))
443 || (e1
== true_edge
&& integer_onep (arg1
))
444 || (e1
== false_edge
&& integer_zerop (arg1
)))
446 new = build2 (MODIFY_EXPR
, TREE_TYPE (new_var1
), new_var1
, cond
);
450 tree cond1
= invert_truthvalue (cond
);
453 /* If what we get back is a conditional expression, there is no
454 way that it can be gimple. */
455 if (TREE_CODE (cond
) == COND_EXPR
)
457 release_ssa_name (new_var1
);
461 /* If what we get back is not gimple try to create it as gimple by
462 using a temporary variable. */
463 if (is_gimple_cast (cond
)
464 && !is_gimple_val (TREE_OPERAND (cond
, 0)))
466 tree temp
= TREE_OPERAND (cond
, 0);
467 tree new_var_1
= make_rename_temp (TREE_TYPE (temp
), NULL
);
468 new = build2 (MODIFY_EXPR
, TREE_TYPE (new_var_1
), new_var_1
, temp
);
469 bsi_insert_after (&bsi
, new, BSI_NEW_STMT
);
470 cond
= fold_convert (TREE_TYPE (result
), new_var_1
);
473 if (TREE_CODE (cond
) == TRUTH_NOT_EXPR
474 && !is_gimple_val (TREE_OPERAND (cond
, 0)))
476 release_ssa_name (new_var1
);
480 new = build2 (MODIFY_EXPR
, TREE_TYPE (new_var1
), new_var1
, cond
);
483 bsi_insert_after (&bsi
, new, BSI_NEW_STMT
);
485 SSA_NAME_DEF_STMT (new_var1
) = new;
487 replace_phi_edge_with_variable (cond_bb
, phi_bb
, e1
, phi
, new_var1
);
489 /* Note that we optimized this PHI. */
493 /* The function value_replacement does the main work of doing the value
494 replacement. Return true if the replacement is done. Otherwise return
496 BB is the basic block where the replacement is going to be done on. ARG0
497 is argument 0 from the PHI. Likewise for ARG1. */
500 value_replacement (basic_block cond_bb
, basic_block middle_bb
,
501 basic_block phi_bb
, edge e0
, edge e1
, tree phi
,
502 tree arg0
, tree arg1
)
505 edge true_edge
, false_edge
;
507 /* If the type says honor signed zeros we cannot do this
509 if (HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg1
))))
512 if (!empty_block_p (middle_bb
))
515 cond
= COND_EXPR_COND (last_stmt (cond_bb
));
517 /* This transformation is only valid for equality comparisons. */
518 if (TREE_CODE (cond
) != NE_EXPR
&& TREE_CODE (cond
) != EQ_EXPR
)
521 /* We need to know which is the true edge and which is the false
522 edge so that we know if have abs or negative abs. */
523 extract_true_false_edges_from_block (cond_bb
, &true_edge
, &false_edge
);
525 /* At this point we know we have a COND_EXPR with two successors.
526 One successor is BB, the other successor is an empty block which
527 falls through into BB.
529 The condition for the COND_EXPR is known to be NE_EXPR or EQ_EXPR.
531 There is a single PHI node at the join point (BB) with two arguments.
533 We now need to verify that the two arguments in the PHI node match
534 the two arguments to the equality comparison. */
536 if ((operand_equal_for_phi_arg_p (arg0
, TREE_OPERAND (cond
, 0))
537 && operand_equal_for_phi_arg_p (arg1
, TREE_OPERAND (cond
, 1)))
538 || (operand_equal_for_phi_arg_p (arg1
, TREE_OPERAND (cond
, 0))
539 && operand_equal_for_phi_arg_p (arg0
, TREE_OPERAND (cond
, 1))))
544 /* For NE_EXPR, we want to build an assignment result = arg where
545 arg is the PHI argument associated with the true edge. For
546 EQ_EXPR we want the PHI argument associated with the false edge. */
547 e
= (TREE_CODE (cond
) == NE_EXPR
? true_edge
: false_edge
);
549 /* Unfortunately, E may not reach BB (it may instead have gone to
550 OTHER_BLOCK). If that is the case, then we want the single outgoing
551 edge from OTHER_BLOCK which reaches BB and represents the desired
552 path from COND_BLOCK. */
553 if (e
->dest
== middle_bb
)
554 e
= single_succ_edge (e
->dest
);
556 /* Now we know the incoming edge to BB that has the argument for the
557 RHS of our new assignment statement. */
563 replace_phi_edge_with_variable (cond_bb
, phi_bb
, e1
, phi
, arg
);
565 /* Note that we optimized this PHI. */
571 /* The function minmax_replacement does the main work of doing the minmax
572 replacement. Return true if the replacement is done. Otherwise return
574 BB is the basic block where the replacement is going to be done on. ARG0
575 is argument 0 from the PHI. Likewise for ARG1. */
578 minmax_replacement (basic_block cond_bb
, basic_block middle_bb
,
579 basic_block phi_bb
, edge e0
, edge e1
, tree phi
,
580 tree arg0
, tree arg1
)
584 edge true_edge
, false_edge
;
585 enum tree_code cmp
, minmax
, ass_code
;
586 tree smaller
, larger
, arg_true
, arg_false
;
587 block_stmt_iterator bsi
, bsi_from
;
589 type
= TREE_TYPE (PHI_RESULT (phi
));
591 /* The optimization may be unsafe due to NaNs. */
592 if (HONOR_NANS (TYPE_MODE (type
)))
595 cond
= COND_EXPR_COND (last_stmt (cond_bb
));
596 cmp
= TREE_CODE (cond
);
597 result
= PHI_RESULT (phi
);
599 /* This transformation is only valid for order comparisons. Record which
600 operand is smaller/larger if the result of the comparison is true. */
601 if (cmp
== LT_EXPR
|| cmp
== LE_EXPR
)
603 smaller
= TREE_OPERAND (cond
, 0);
604 larger
= TREE_OPERAND (cond
, 1);
606 else if (cmp
== GT_EXPR
|| cmp
== GE_EXPR
)
608 smaller
= TREE_OPERAND (cond
, 1);
609 larger
= TREE_OPERAND (cond
, 0);
614 /* We need to know which is the true edge and which is the false
615 edge so that we know if have abs or negative abs. */
616 extract_true_false_edges_from_block (cond_bb
, &true_edge
, &false_edge
);
618 /* Forward the edges over the middle basic block. */
619 if (true_edge
->dest
== middle_bb
)
620 true_edge
= EDGE_SUCC (true_edge
->dest
, 0);
621 if (false_edge
->dest
== middle_bb
)
622 false_edge
= EDGE_SUCC (false_edge
->dest
, 0);
626 gcc_assert (false_edge
== e1
);
632 gcc_assert (false_edge
== e0
);
633 gcc_assert (true_edge
== e1
);
638 if (empty_block_p (middle_bb
))
640 if (operand_equal_for_phi_arg_p (arg_true
, smaller
)
641 && operand_equal_for_phi_arg_p (arg_false
, larger
))
645 if (smaller < larger)
651 else if (operand_equal_for_phi_arg_p (arg_false
, smaller
)
652 && operand_equal_for_phi_arg_p (arg_true
, larger
))
659 /* Recognize the following case, assuming d <= u:
665 This is equivalent to
670 tree assign
= last_and_only_stmt (middle_bb
);
671 tree lhs
, rhs
, op0
, op1
, bound
;
674 || TREE_CODE (assign
) != MODIFY_EXPR
)
677 lhs
= TREE_OPERAND (assign
, 0);
678 rhs
= TREE_OPERAND (assign
, 1);
679 ass_code
= TREE_CODE (rhs
);
680 if (ass_code
!= MAX_EXPR
&& ass_code
!= MIN_EXPR
)
682 op0
= TREE_OPERAND (rhs
, 0);
683 op1
= TREE_OPERAND (rhs
, 1);
685 if (true_edge
->src
== middle_bb
)
687 /* We got here if the condition is true, i.e., SMALLER < LARGER. */
688 if (!operand_equal_for_phi_arg_p (lhs
, arg_true
))
691 if (operand_equal_for_phi_arg_p (arg_false
, larger
))
695 if (smaller < larger)
697 r' = MAX_EXPR (smaller, bound)
699 r = PHI <r', larger> --> to be turned to MIN_EXPR. */
700 if (ass_code
!= MAX_EXPR
)
704 if (operand_equal_for_phi_arg_p (op0
, smaller
))
706 else if (operand_equal_for_phi_arg_p (op1
, smaller
))
711 /* We need BOUND <= LARGER. */
712 if (!integer_nonzerop (fold (build2 (LE_EXPR
, boolean_type_node
,
716 else if (operand_equal_for_phi_arg_p (arg_false
, smaller
))
720 if (smaller < larger)
722 r' = MIN_EXPR (larger, bound)
724 r = PHI <r', smaller> --> to be turned to MAX_EXPR. */
725 if (ass_code
!= MIN_EXPR
)
729 if (operand_equal_for_phi_arg_p (op0
, larger
))
731 else if (operand_equal_for_phi_arg_p (op1
, larger
))
736 /* We need BOUND >= SMALLER. */
737 if (!integer_nonzerop (fold (build2 (GE_EXPR
, boolean_type_node
,
746 /* We got here if the condition is false, i.e., SMALLER > LARGER. */
747 if (!operand_equal_for_phi_arg_p (lhs
, arg_false
))
750 if (operand_equal_for_phi_arg_p (arg_true
, larger
))
754 if (smaller > larger)
756 r' = MIN_EXPR (smaller, bound)
758 r = PHI <r', larger> --> to be turned to MAX_EXPR. */
759 if (ass_code
!= MIN_EXPR
)
763 if (operand_equal_for_phi_arg_p (op0
, smaller
))
765 else if (operand_equal_for_phi_arg_p (op1
, smaller
))
770 /* We need BOUND >= LARGER. */
771 if (!integer_nonzerop (fold (build2 (GE_EXPR
, boolean_type_node
,
775 else if (operand_equal_for_phi_arg_p (arg_true
, smaller
))
779 if (smaller > larger)
781 r' = MAX_EXPR (larger, bound)
783 r = PHI <r', smaller> --> to be turned to MIN_EXPR. */
784 if (ass_code
!= MAX_EXPR
)
788 if (operand_equal_for_phi_arg_p (op0
, larger
))
790 else if (operand_equal_for_phi_arg_p (op1
, larger
))
795 /* We need BOUND <= SMALLER. */
796 if (!integer_nonzerop (fold (build2 (LE_EXPR
, boolean_type_node
,
804 /* Move the statement from the middle block. */
805 bsi
= bsi_last (cond_bb
);
806 bsi_from
= bsi_last (middle_bb
);
807 bsi_move_before (&bsi_from
, &bsi
);
810 /* Emit the statement to compute min/max. */
811 result
= duplicate_ssa_name (PHI_RESULT (phi
), NULL
);
812 new = build2 (MODIFY_EXPR
, type
, result
,
813 build2 (minmax
, type
, arg0
, arg1
));
814 SSA_NAME_DEF_STMT (result
) = new;
815 bsi
= bsi_last (cond_bb
);
816 bsi_insert_before (&bsi
, new, BSI_NEW_STMT
);
818 replace_phi_edge_with_variable (cond_bb
, phi_bb
, e1
, phi
, result
);
822 /* The function absolute_replacement does the main work of doing the absolute
823 replacement. Return true if the replacement is done. Otherwise return
825 bb is the basic block where the replacement is going to be done on. arg0
826 is argument 0 from the phi. Likewise for arg1. */
829 abs_replacement (basic_block cond_bb
, basic_block middle_bb
,
830 basic_block phi_bb
, edge e0 ATTRIBUTE_UNUSED
, edge e1
,
831 tree phi
, tree arg0
, tree arg1
)
835 block_stmt_iterator bsi
;
836 edge true_edge
, false_edge
;
841 enum tree_code cond_code
;
843 /* If the type says honor signed zeros we cannot do this
845 if (HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg1
))))
848 /* OTHER_BLOCK must have only one executable statement which must have the
849 form arg0 = -arg1 or arg1 = -arg0. */
851 assign
= last_and_only_stmt (middle_bb
);
852 /* If we did not find the proper negation assignment, then we can not
857 /* If we got here, then we have found the only executable statement
858 in OTHER_BLOCK. If it is anything other than arg = -arg1 or
859 arg1 = -arg0, then we can not optimize. */
860 if (TREE_CODE (assign
) != MODIFY_EXPR
)
863 lhs
= TREE_OPERAND (assign
, 0);
864 rhs
= TREE_OPERAND (assign
, 1);
866 if (TREE_CODE (rhs
) != NEGATE_EXPR
)
869 rhs
= TREE_OPERAND (rhs
, 0);
871 /* The assignment has to be arg0 = -arg1 or arg1 = -arg0. */
872 if (!(lhs
== arg0
&& rhs
== arg1
)
873 && !(lhs
== arg1
&& rhs
== arg0
))
876 cond
= COND_EXPR_COND (last_stmt (cond_bb
));
877 result
= PHI_RESULT (phi
);
879 /* Only relationals comparing arg[01] against zero are interesting. */
880 cond_code
= TREE_CODE (cond
);
881 if (cond_code
!= GT_EXPR
&& cond_code
!= GE_EXPR
882 && cond_code
!= LT_EXPR
&& cond_code
!= LE_EXPR
)
885 /* Make sure the conditional is arg[01] OP y. */
886 if (TREE_OPERAND (cond
, 0) != rhs
)
889 if (FLOAT_TYPE_P (TREE_TYPE (TREE_OPERAND (cond
, 1)))
890 ? real_zerop (TREE_OPERAND (cond
, 1))
891 : integer_zerop (TREE_OPERAND (cond
, 1)))
896 /* We need to know which is the true edge and which is the false
897 edge so that we know if have abs or negative abs. */
898 extract_true_false_edges_from_block (cond_bb
, &true_edge
, &false_edge
);
900 /* For GT_EXPR/GE_EXPR, if the true edge goes to OTHER_BLOCK, then we
901 will need to negate the result. Similarly for LT_EXPR/LE_EXPR if
902 the false edge goes to OTHER_BLOCK. */
903 if (cond_code
== GT_EXPR
|| cond_code
== GE_EXPR
)
908 if (e
->dest
== middle_bb
)
913 result
= duplicate_ssa_name (result
, NULL
);
916 lhs
= make_rename_temp (TREE_TYPE (result
), NULL
);
920 /* Build the modify expression with abs expression. */
921 new = build2 (MODIFY_EXPR
, TREE_TYPE (lhs
),
922 lhs
, build1 (ABS_EXPR
, TREE_TYPE (lhs
), rhs
));
924 bsi
= bsi_last (cond_bb
);
925 bsi_insert_before (&bsi
, new, BSI_NEW_STMT
);
929 /* Get the right BSI. We want to insert after the recently
930 added ABS_EXPR statement (which we know is the first statement
932 new = build2 (MODIFY_EXPR
, TREE_TYPE (result
),
933 result
, build1 (NEGATE_EXPR
, TREE_TYPE (lhs
), lhs
));
935 bsi_insert_after (&bsi
, new, BSI_NEW_STMT
);
938 SSA_NAME_DEF_STMT (result
) = new;
939 replace_phi_edge_with_variable (cond_bb
, phi_bb
, e1
, phi
, result
);
941 /* Note that we optimized this PHI. */
946 /* Always do these optimizations if we have SSA
954 struct tree_opt_pass pass_phiopt
=
957 gate_phiopt
, /* gate */
958 tree_ssa_phiopt
, /* execute */
961 0, /* static_pass_number */
962 TV_TREE_PHIOPT
, /* tv_id */
963 PROP_cfg
| PROP_ssa
| PROP_alias
, /* properties_required */
964 0, /* properties_provided */
965 0, /* properties_destroyed */
966 0, /* todo_flags_start */
973 | TODO_verify_stmts
, /* todo_flags_finish */