annotate gcc/tree-ssa-dce.c @ 131:84e7813d76e9

gcc-8.2
author mir3636
date Thu, 25 Oct 2018 07:37:49 +0900
parents 04ced10e8804
children 1830386684a0
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1 /* Dead code elimination pass for the GNU compiler.
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
2 Copyright (C) 2002-2018 Free Software Foundation, Inc.
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
3 Contributed by Ben Elliston <bje@redhat.com>
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
4 and Andrew MacLeod <amacleod@redhat.com>
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
5 Adapted to use control dependence by Steven Bosscher, SUSE Labs.
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
6
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
7 This file is part of GCC.
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
8
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
9 GCC is free software; you can redistribute it and/or modify it
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
10 under the terms of the GNU General Public License as published by the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
11 Free Software Foundation; either version 3, or (at your option) any
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
12 later version.
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
13
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
14 GCC is distributed in the hope that it will be useful, but WITHOUT
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
15 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
17 for more details.
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
18
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
19 You should have received a copy of the GNU General Public License
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
20 along with GCC; see the file COPYING3. If not see
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
21 <http://www.gnu.org/licenses/>. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
22
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
23 /* Dead code elimination.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
24
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
25 References:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
26
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
27 Building an Optimizing Compiler,
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
28 Robert Morgan, Butterworth-Heinemann, 1998, Section 8.9.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
29
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
30 Advanced Compiler Design and Implementation,
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
31 Steven Muchnick, Morgan Kaufmann, 1997, Section 18.10.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
32
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
33 Dead-code elimination is the removal of statements which have no
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
34 impact on the program's output. "Dead statements" have no impact
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
35 on the program's output, while "necessary statements" may have
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
36 impact on the output.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
37
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
38 The algorithm consists of three phases:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
39 1. Marking as necessary all statements known to be necessary,
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
40 e.g. most function calls, writing a value to memory, etc;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
41 2. Propagating necessary statements, e.g., the statements
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
42 giving values to operands in necessary statements; and
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
43 3. Removing dead statements. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
44
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
45 #include "config.h"
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
46 #include "system.h"
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
47 #include "coretypes.h"
111
kono
parents: 67
diff changeset
48 #include "backend.h"
kono
parents: 67
diff changeset
49 #include "rtl.h"
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
50 #include "tree.h"
111
kono
parents: 67
diff changeset
51 #include "gimple.h"
kono
parents: 67
diff changeset
52 #include "cfghooks.h"
kono
parents: 67
diff changeset
53 #include "tree-pass.h"
kono
parents: 67
diff changeset
54 #include "ssa.h"
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
55 #include "gimple-pretty-print.h"
111
kono
parents: 67
diff changeset
56 #include "fold-const.h"
kono
parents: 67
diff changeset
57 #include "calls.h"
kono
parents: 67
diff changeset
58 #include "cfganal.h"
kono
parents: 67
diff changeset
59 #include "tree-eh.h"
kono
parents: 67
diff changeset
60 #include "gimplify.h"
kono
parents: 67
diff changeset
61 #include "gimple-iterator.h"
kono
parents: 67
diff changeset
62 #include "tree-cfg.h"
kono
parents: 67
diff changeset
63 #include "tree-ssa-loop-niter.h"
kono
parents: 67
diff changeset
64 #include "tree-into-ssa.h"
kono
parents: 67
diff changeset
65 #include "tree-dfa.h"
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
66 #include "cfgloop.h"
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
67 #include "tree-scalar-evolution.h"
111
kono
parents: 67
diff changeset
68 #include "tree-ssa-propagate.h"
kono
parents: 67
diff changeset
69 #include "gimple-fold.h"
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
70
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
71 static struct stmt_stats
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
72 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
73 int total;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
74 int total_phis;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
75 int removed;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
76 int removed_phis;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
77 } stats;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
78
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
79 #define STMT_NECESSARY GF_PLF_1
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
80
111
kono
parents: 67
diff changeset
81 static vec<gimple *> worklist;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
82
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
83 /* Vector indicating an SSA name has already been processed and marked
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
84 as necessary. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
85 static sbitmap processed;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
86
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
87 /* Vector indicating that the last statement of a basic block has already
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
88 been marked as necessary. */
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
89 static sbitmap last_stmt_necessary;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
90
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
91 /* Vector indicating that BB contains statements that are live. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
92 static sbitmap bb_contains_live_stmts;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
93
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
94 /* Before we can determine whether a control branch is dead, we need to
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
95 compute which blocks are control dependent on which edges.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
96
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
97 We expect each block to be control dependent on very few edges so we
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
98 use a bitmap for each block recording its edges. An array holds the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
99 bitmap. The Ith bit in the bitmap is set if that block is dependent
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
100 on the Ith edge. */
111
kono
parents: 67
diff changeset
101 static control_dependences *cd;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
102
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
103 /* Vector indicating that a basic block has already had all the edges
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
104 processed that it is control dependent on. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
105 static sbitmap visited_control_parents;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
106
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
107 /* TRUE if this pass alters the CFG (by removing control statements).
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
108 FALSE otherwise.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
109
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
110 If this pass alters the CFG, then it will arrange for the dominators
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
111 to be recomputed. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
112 static bool cfg_altered;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
113
111
kono
parents: 67
diff changeset
114 /* When non-NULL holds map from basic block index into the postorder. */
kono
parents: 67
diff changeset
115 static int *bb_postorder;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
116
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
117
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
118 /* If STMT is not already marked necessary, mark it, and add it to the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
119 worklist if ADD_TO_WORKLIST is true. */
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
120
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
121 static inline void
111
kono
parents: 67
diff changeset
122 mark_stmt_necessary (gimple *stmt, bool add_to_worklist)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
123 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
124 gcc_assert (stmt);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
125
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
126 if (gimple_plf (stmt, STMT_NECESSARY))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
127 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
128
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
129 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
130 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
131 fprintf (dump_file, "Marking useful stmt: ");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
132 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
133 fprintf (dump_file, "\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
134 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
135
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
136 gimple_set_plf (stmt, STMT_NECESSARY, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
137 if (add_to_worklist)
111
kono
parents: 67
diff changeset
138 worklist.safe_push (stmt);
kono
parents: 67
diff changeset
139 if (add_to_worklist && bb_contains_live_stmts && !is_gimple_debug (stmt))
kono
parents: 67
diff changeset
140 bitmap_set_bit (bb_contains_live_stmts, gimple_bb (stmt)->index);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
141 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
142
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
143
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
144 /* Mark the statement defining operand OP as necessary. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
145
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
146 static inline void
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
147 mark_operand_necessary (tree op)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
148 {
111
kono
parents: 67
diff changeset
149 gimple *stmt;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
150 int ver;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
151
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
152 gcc_assert (op);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
153
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
154 ver = SSA_NAME_VERSION (op);
111
kono
parents: 67
diff changeset
155 if (bitmap_bit_p (processed, ver))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
156 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
157 stmt = SSA_NAME_DEF_STMT (op);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
158 gcc_assert (gimple_nop_p (stmt)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
159 || gimple_plf (stmt, STMT_NECESSARY));
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
160 return;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
161 }
111
kono
parents: 67
diff changeset
162 bitmap_set_bit (processed, ver);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
163
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
164 stmt = SSA_NAME_DEF_STMT (op);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
165 gcc_assert (stmt);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
166
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
167 if (gimple_plf (stmt, STMT_NECESSARY) || gimple_nop_p (stmt))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
168 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
169
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
170 if (dump_file && (dump_flags & TDF_DETAILS))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
171 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
172 fprintf (dump_file, "marking necessary through ");
111
kono
parents: 67
diff changeset
173 print_generic_expr (dump_file, op);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
174 fprintf (dump_file, " stmt ");
111
kono
parents: 67
diff changeset
175 print_gimple_stmt (dump_file, stmt, 0);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
176 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
177
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
178 gimple_set_plf (stmt, STMT_NECESSARY, true);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
179 if (bb_contains_live_stmts)
111
kono
parents: 67
diff changeset
180 bitmap_set_bit (bb_contains_live_stmts, gimple_bb (stmt)->index);
kono
parents: 67
diff changeset
181 worklist.safe_push (stmt);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
182 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
183
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
184
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
185 /* Mark STMT as necessary if it obviously is. Add it to the worklist if
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
186 it can make other statements necessary.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
187
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
188 If AGGRESSIVE is false, control statements are conservatively marked as
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
189 necessary. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
190
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
191 static void
111
kono
parents: 67
diff changeset
192 mark_stmt_if_obviously_necessary (gimple *stmt, bool aggressive)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
193 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
194 /* With non-call exceptions, we have to assume that all statements could
111
kono
parents: 67
diff changeset
195 throw. If a statement could throw, it can be deemed necessary. */
kono
parents: 67
diff changeset
196 if (cfun->can_throw_non_call_exceptions
kono
parents: 67
diff changeset
197 && !cfun->can_delete_dead_exceptions
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
198 && stmt_could_throw_p (cfun, stmt))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
199 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
200 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
201 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
202 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
203
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
204 /* Statements that are implicitly live. Most function calls, asm
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
205 and return statements are required. Labels and GIMPLE_BIND nodes
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
206 are kept because they are control flow, and we have no way of
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
207 knowing whether they can be removed. DCE can eliminate all the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
208 other statements in a block, and CFG can then remove the block
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
209 and labels. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
210 switch (gimple_code (stmt))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
211 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
212 case GIMPLE_PREDICT:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
213 case GIMPLE_LABEL:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
214 mark_stmt_necessary (stmt, false);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
215 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
216
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
217 case GIMPLE_ASM:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
218 case GIMPLE_RESX:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
219 case GIMPLE_RETURN:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
220 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
221 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
222
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
223 case GIMPLE_CALL:
111
kono
parents: 67
diff changeset
224 {
kono
parents: 67
diff changeset
225 tree callee = gimple_call_fndecl (stmt);
kono
parents: 67
diff changeset
226 if (callee != NULL_TREE
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
227 && fndecl_built_in_p (callee, BUILT_IN_NORMAL))
111
kono
parents: 67
diff changeset
228 switch (DECL_FUNCTION_CODE (callee))
kono
parents: 67
diff changeset
229 {
kono
parents: 67
diff changeset
230 case BUILT_IN_MALLOC:
kono
parents: 67
diff changeset
231 case BUILT_IN_ALIGNED_ALLOC:
kono
parents: 67
diff changeset
232 case BUILT_IN_CALLOC:
kono
parents: 67
diff changeset
233 CASE_BUILT_IN_ALLOCA:
kono
parents: 67
diff changeset
234 case BUILT_IN_STRDUP:
kono
parents: 67
diff changeset
235 case BUILT_IN_STRNDUP:
kono
parents: 67
diff changeset
236 return;
kono
parents: 67
diff changeset
237
kono
parents: 67
diff changeset
238 default:;
kono
parents: 67
diff changeset
239 }
kono
parents: 67
diff changeset
240 /* Most, but not all function calls are required. Function calls that
kono
parents: 67
diff changeset
241 produce no result and have no side effects (i.e. const pure
kono
parents: 67
diff changeset
242 functions) are unnecessary. */
kono
parents: 67
diff changeset
243 if (gimple_has_side_effects (stmt))
kono
parents: 67
diff changeset
244 {
kono
parents: 67
diff changeset
245 mark_stmt_necessary (stmt, true);
kono
parents: 67
diff changeset
246 return;
kono
parents: 67
diff changeset
247 }
kono
parents: 67
diff changeset
248 if (!gimple_call_lhs (stmt))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
249 return;
111
kono
parents: 67
diff changeset
250 break;
kono
parents: 67
diff changeset
251 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
252
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
253 case GIMPLE_DEBUG:
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
254 /* Debug temps without a value are not useful. ??? If we could
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
255 easily locate the debug temp bind stmt for a use thereof,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
256 would could refrain from marking all debug temps here, and
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
257 mark them only if they're used. */
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
258 if (gimple_debug_nonbind_marker_p (stmt)
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
259 || !gimple_debug_bind_p (stmt)
111
kono
parents: 67
diff changeset
260 || gimple_debug_bind_has_value_p (stmt)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
261 || TREE_CODE (gimple_debug_bind_get_var (stmt)) != DEBUG_EXPR_DECL)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
262 mark_stmt_necessary (stmt, false);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
263 return;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
264
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
265 case GIMPLE_GOTO:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
266 gcc_assert (!simple_goto_p (stmt));
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
267 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
268 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
269
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
270 case GIMPLE_COND:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
271 gcc_assert (EDGE_COUNT (gimple_bb (stmt)->succs) == 2);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
272 /* Fall through. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
273
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
274 case GIMPLE_SWITCH:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
275 if (! aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
276 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
277 break;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
278
111
kono
parents: 67
diff changeset
279 case GIMPLE_ASSIGN:
kono
parents: 67
diff changeset
280 if (gimple_clobber_p (stmt))
kono
parents: 67
diff changeset
281 return;
kono
parents: 67
diff changeset
282 break;
kono
parents: 67
diff changeset
283
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
284 default:
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
285 break;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
286 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
287
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
288 /* If the statement has volatile operands, it needs to be preserved.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
289 Same for statements that can alter control flow in unpredictable
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
290 ways. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
291 if (gimple_has_volatile_ops (stmt) || is_ctrl_altering_stmt (stmt))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
292 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
293 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
294 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
295 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
296
111
kono
parents: 67
diff changeset
297 if (stmt_may_clobber_global_p (stmt))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
298 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
299 mark_stmt_necessary (stmt, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
300 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
301 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
302
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
303 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
304 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
305
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
306
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
307 /* Mark the last statement of BB as necessary. */
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
308
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
309 static void
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
310 mark_last_stmt_necessary (basic_block bb)
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
311 {
111
kono
parents: 67
diff changeset
312 gimple *stmt = last_stmt (bb);
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
313
111
kono
parents: 67
diff changeset
314 bitmap_set_bit (last_stmt_necessary, bb->index);
kono
parents: 67
diff changeset
315 bitmap_set_bit (bb_contains_live_stmts, bb->index);
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
316
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
317 /* We actually mark the statement only if it is a control statement. */
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
318 if (stmt && is_ctrl_stmt (stmt))
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
319 mark_stmt_necessary (stmt, true);
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
320 }
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
321
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
322
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
323 /* Mark control dependent edges of BB as necessary. We have to do this only
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
324 once for each basic block so we set the appropriate bit after we're done.
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
325
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
326 When IGNORE_SELF is true, ignore BB in the list of control dependences. */
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
327
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
328 static void
111
kono
parents: 67
diff changeset
329 mark_control_dependent_edges_necessary (basic_block bb, bool ignore_self)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
330 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
331 bitmap_iterator bi;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
332 unsigned edge_number;
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
333 bool skipped = false;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
334
111
kono
parents: 67
diff changeset
335 gcc_assert (bb != EXIT_BLOCK_PTR_FOR_FN (cfun));
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
336
111
kono
parents: 67
diff changeset
337 if (bb == ENTRY_BLOCK_PTR_FOR_FN (cfun))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
338 return;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
339
111
kono
parents: 67
diff changeset
340 EXECUTE_IF_SET_IN_BITMAP (cd->get_edges_dependent_on (bb->index),
kono
parents: 67
diff changeset
341 0, edge_number, bi)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
342 {
111
kono
parents: 67
diff changeset
343 basic_block cd_bb = cd->get_edge_src (edge_number);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
344
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
345 if (ignore_self && cd_bb == bb)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
346 {
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
347 skipped = true;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
348 continue;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
349 }
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
350
111
kono
parents: 67
diff changeset
351 if (!bitmap_bit_p (last_stmt_necessary, cd_bb->index))
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
352 mark_last_stmt_necessary (cd_bb);
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
353 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
354
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
355 if (!skipped)
111
kono
parents: 67
diff changeset
356 bitmap_set_bit (visited_control_parents, bb->index);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
357 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
358
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
359
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
360 /* Find obviously necessary statements. These are things like most function
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
361 calls, and stores to file level variables.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
362
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
363 If EL is NULL, control statements are conservatively marked as
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
364 necessary. Otherwise it contains the list of edges used by control
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
365 dependence analysis. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
366
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
367 static void
111
kono
parents: 67
diff changeset
368 find_obviously_necessary_stmts (bool aggressive)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
369 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
370 basic_block bb;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
371 gimple_stmt_iterator gsi;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
372 edge e;
111
kono
parents: 67
diff changeset
373 gimple *phi, *stmt;
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
374 int flags;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
375
111
kono
parents: 67
diff changeset
376 FOR_EACH_BB_FN (bb, cfun)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
377 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
378 /* PHI nodes are never inherently necessary. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
379 for (gsi = gsi_start_phis (bb); !gsi_end_p (gsi); gsi_next (&gsi))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
380 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
381 phi = gsi_stmt (gsi);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
382 gimple_set_plf (phi, STMT_NECESSARY, false);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
383 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
384
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
385 /* Check all statements in the block. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
386 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
387 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
388 stmt = gsi_stmt (gsi);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
389 gimple_set_plf (stmt, STMT_NECESSARY, false);
111
kono
parents: 67
diff changeset
390 mark_stmt_if_obviously_necessary (stmt, aggressive);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
391 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
392 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
393
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
394 /* Pure and const functions are finite and thus have no infinite loops in
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
395 them. */
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
396 flags = flags_from_decl_or_type (current_function_decl);
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
397 if ((flags & (ECF_CONST|ECF_PURE)) && !(flags & ECF_LOOPING_CONST_OR_PURE))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
398 return;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
399
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
400 /* Prevent the empty possibly infinite loops from being removed. */
111
kono
parents: 67
diff changeset
401 if (aggressive)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
402 {
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
403 struct loop *loop;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
404 if (mark_irreducible_loops ())
111
kono
parents: 67
diff changeset
405 FOR_EACH_BB_FN (bb, cfun)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
406 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
407 edge_iterator ei;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
408 FOR_EACH_EDGE (e, ei, bb->succs)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
409 if ((e->flags & EDGE_DFS_BACK)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
410 && (e->flags & EDGE_IRREDUCIBLE_LOOP))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
411 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
412 if (dump_file)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
413 fprintf (dump_file, "Marking back edge of irreducible loop %i->%i\n",
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
414 e->src->index, e->dest->index);
111
kono
parents: 67
diff changeset
415 mark_control_dependent_edges_necessary (e->dest, false);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
416 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
417 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
418
111
kono
parents: 67
diff changeset
419 FOR_EACH_LOOP (loop, 0)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
420 if (!finite_loop_p (loop))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
421 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
422 if (dump_file)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
423 fprintf (dump_file, "can not prove finiteness of loop %i\n", loop->num);
111
kono
parents: 67
diff changeset
424 mark_control_dependent_edges_necessary (loop->latch, false);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
425 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
426 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
427 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
428
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
429
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
430 /* Return true if REF is based on an aliased base, otherwise false. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
431
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
432 static bool
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
433 ref_may_be_aliased (tree ref)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
434 {
111
kono
parents: 67
diff changeset
435 gcc_assert (TREE_CODE (ref) != WITH_SIZE_EXPR);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
436 while (handled_component_p (ref))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
437 ref = TREE_OPERAND (ref, 0);
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
438 if (TREE_CODE (ref) == MEM_REF
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
439 && TREE_CODE (TREE_OPERAND (ref, 0)) == ADDR_EXPR)
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
440 ref = TREE_OPERAND (TREE_OPERAND (ref, 0), 0);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
441 return !(DECL_P (ref)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
442 && !may_be_aliased (ref));
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
443 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
444
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
445 static bitmap visited = NULL;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
446 static unsigned int longest_chain = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
447 static unsigned int total_chain = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
448 static unsigned int nr_walks = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
449 static bool chain_ovfl = false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
450
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
451 /* Worker for the walker that marks reaching definitions of REF,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
452 which is based on a non-aliased decl, necessary. It returns
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
453 true whenever the defining statement of the current VDEF is
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
454 a kill for REF, as no dominating may-defs are necessary for REF
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
455 anymore. DATA points to the basic-block that contains the
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
456 stmt that refers to REF. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
457
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
458 static bool
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
459 mark_aliased_reaching_defs_necessary_1 (ao_ref *ref, tree vdef, void *data)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
460 {
111
kono
parents: 67
diff changeset
461 gimple *def_stmt = SSA_NAME_DEF_STMT (vdef);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
462
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
463 /* All stmts we visit are necessary. */
111
kono
parents: 67
diff changeset
464 if (! gimple_clobber_p (def_stmt))
kono
parents: 67
diff changeset
465 mark_operand_necessary (vdef);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
466
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
467 /* If the stmt lhs kills ref, then we can stop walking. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
468 if (gimple_has_lhs (def_stmt)
111
kono
parents: 67
diff changeset
469 && TREE_CODE (gimple_get_lhs (def_stmt)) != SSA_NAME
kono
parents: 67
diff changeset
470 /* The assignment is not necessarily carried out if it can throw
kono
parents: 67
diff changeset
471 and we can catch it in the current function where we could inspect
kono
parents: 67
diff changeset
472 the previous value.
kono
parents: 67
diff changeset
473 ??? We only need to care about the RHS throwing. For aggregate
kono
parents: 67
diff changeset
474 assignments or similar calls and non-call exceptions the LHS
kono
parents: 67
diff changeset
475 might throw as well. */
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
476 && !stmt_can_throw_internal (cfun, def_stmt))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
477 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
478 tree base, lhs = gimple_get_lhs (def_stmt);
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
479 poly_int64 size, offset, max_size;
111
kono
parents: 67
diff changeset
480 bool reverse;
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
481 ao_ref_base (ref);
111
kono
parents: 67
diff changeset
482 base
kono
parents: 67
diff changeset
483 = get_ref_base_and_extent (lhs, &offset, &size, &max_size, &reverse);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
484 /* We can get MEM[symbol: sZ, index: D.8862_1] here,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
485 so base == refd->base does not always hold. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
486 if (base == ref->base)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
487 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
488 /* For a must-alias check we need to be able to constrain
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
489 the accesses properly. */
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
490 if (known_eq (size, max_size)
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
491 && known_subrange_p (ref->offset, ref->max_size, offset, size))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
492 return true;
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
493 /* Or they need to be exactly the same. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
494 else if (ref->ref
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
495 /* Make sure there is no induction variable involved
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
496 in the references (gcc.c-torture/execute/pr42142.c).
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
497 The simplest way is to check if the kill dominates
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
498 the use. */
111
kono
parents: 67
diff changeset
499 /* But when both are in the same block we cannot
kono
parents: 67
diff changeset
500 easily tell whether we came from a backedge
kono
parents: 67
diff changeset
501 unless we decide to compute stmt UIDs
kono
parents: 67
diff changeset
502 (see PR58246). */
kono
parents: 67
diff changeset
503 && (basic_block) data != gimple_bb (def_stmt)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
504 && dominated_by_p (CDI_DOMINATORS, (basic_block) data,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
505 gimple_bb (def_stmt))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
506 && operand_equal_p (ref->ref, lhs, 0))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
507 return true;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
508 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
509 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
510
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
511 /* Otherwise keep walking. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
512 return false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
513 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
514
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
515 static void
111
kono
parents: 67
diff changeset
516 mark_aliased_reaching_defs_necessary (gimple *stmt, tree ref)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
517 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
518 unsigned int chain;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
519 ao_ref refd;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
520 gcc_assert (!chain_ovfl);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
521 ao_ref_init (&refd, ref);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
522 chain = walk_aliased_vdefs (&refd, gimple_vuse (stmt),
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
523 mark_aliased_reaching_defs_necessary_1,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
524 gimple_bb (stmt), NULL);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
525 if (chain > longest_chain)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
526 longest_chain = chain;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
527 total_chain += chain;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
528 nr_walks++;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
529 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
530
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
531 /* Worker for the walker that marks reaching definitions of REF, which
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
532 is not based on a non-aliased decl. For simplicity we need to end
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
533 up marking all may-defs necessary that are not based on a non-aliased
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
534 decl. The only job of this walker is to skip may-defs based on
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
535 a non-aliased decl. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
536
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
537 static bool
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
538 mark_all_reaching_defs_necessary_1 (ao_ref *ref ATTRIBUTE_UNUSED,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
539 tree vdef, void *data ATTRIBUTE_UNUSED)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
540 {
111
kono
parents: 67
diff changeset
541 gimple *def_stmt = SSA_NAME_DEF_STMT (vdef);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
542
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
543 /* We have to skip already visited (and thus necessary) statements
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
544 to make the chaining work after we dropped back to simple mode. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
545 if (chain_ovfl
111
kono
parents: 67
diff changeset
546 && bitmap_bit_p (processed, SSA_NAME_VERSION (vdef)))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
547 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
548 gcc_assert (gimple_nop_p (def_stmt)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
549 || gimple_plf (def_stmt, STMT_NECESSARY));
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
550 return false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
551 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
552
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
553 /* We want to skip stores to non-aliased variables. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
554 if (!chain_ovfl
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
555 && gimple_assign_single_p (def_stmt))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
556 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
557 tree lhs = gimple_assign_lhs (def_stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
558 if (!ref_may_be_aliased (lhs))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
559 return false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
560 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
561
111
kono
parents: 67
diff changeset
562 /* We want to skip statments that do not constitute stores but have
kono
parents: 67
diff changeset
563 a virtual definition. */
kono
parents: 67
diff changeset
564 if (is_gimple_call (def_stmt))
kono
parents: 67
diff changeset
565 {
kono
parents: 67
diff changeset
566 tree callee = gimple_call_fndecl (def_stmt);
kono
parents: 67
diff changeset
567 if (callee != NULL_TREE
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
568 && fndecl_built_in_p (callee, BUILT_IN_NORMAL))
111
kono
parents: 67
diff changeset
569 switch (DECL_FUNCTION_CODE (callee))
kono
parents: 67
diff changeset
570 {
kono
parents: 67
diff changeset
571 case BUILT_IN_MALLOC:
kono
parents: 67
diff changeset
572 case BUILT_IN_ALIGNED_ALLOC:
kono
parents: 67
diff changeset
573 case BUILT_IN_CALLOC:
kono
parents: 67
diff changeset
574 CASE_BUILT_IN_ALLOCA:
kono
parents: 67
diff changeset
575 case BUILT_IN_FREE:
kono
parents: 67
diff changeset
576 return false;
kono
parents: 67
diff changeset
577
kono
parents: 67
diff changeset
578 default:;
kono
parents: 67
diff changeset
579 }
kono
parents: 67
diff changeset
580 }
kono
parents: 67
diff changeset
581
kono
parents: 67
diff changeset
582 if (! gimple_clobber_p (def_stmt))
kono
parents: 67
diff changeset
583 mark_operand_necessary (vdef);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
584
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
585 return false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
586 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
587
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
588 static void
111
kono
parents: 67
diff changeset
589 mark_all_reaching_defs_necessary (gimple *stmt)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
590 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
591 walk_aliased_vdefs (NULL, gimple_vuse (stmt),
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
592 mark_all_reaching_defs_necessary_1, NULL, &visited);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
593 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
594
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
595 /* Return true for PHI nodes with one or identical arguments
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
596 can be removed. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
597 static bool
111
kono
parents: 67
diff changeset
598 degenerate_phi_p (gimple *phi)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
599 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
600 unsigned int i;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
601 tree op = gimple_phi_arg_def (phi, 0);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
602 for (i = 1; i < gimple_phi_num_args (phi); i++)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
603 if (gimple_phi_arg_def (phi, i) != op)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
604 return false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
605 return true;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
606 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
607
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
608 /* Propagate necessity using the operands of necessary statements.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
609 Process the uses on each statement in the worklist, and add all
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
610 feeding statements which contribute to the calculation of this
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
611 value to the worklist.
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
612
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
613 In conservative mode, EL is NULL. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
614
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
615 static void
111
kono
parents: 67
diff changeset
616 propagate_necessity (bool aggressive)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
617 {
111
kono
parents: 67
diff changeset
618 gimple *stmt;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
619
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
620 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
621 fprintf (dump_file, "\nProcessing worklist:\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
622
111
kono
parents: 67
diff changeset
623 while (worklist.length () > 0)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
624 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
625 /* Take STMT from worklist. */
111
kono
parents: 67
diff changeset
626 stmt = worklist.pop ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
627
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
628 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
629 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
630 fprintf (dump_file, "processing: ");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
631 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
632 fprintf (dump_file, "\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
633 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
634
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
635 if (aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
636 {
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
637 /* Mark the last statement of the basic blocks on which the block
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
638 containing STMT is control dependent, but only if we haven't
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
639 already done so. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
640 basic_block bb = gimple_bb (stmt);
111
kono
parents: 67
diff changeset
641 if (bb != ENTRY_BLOCK_PTR_FOR_FN (cfun)
kono
parents: 67
diff changeset
642 && !bitmap_bit_p (visited_control_parents, bb->index))
kono
parents: 67
diff changeset
643 mark_control_dependent_edges_necessary (bb, false);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
644 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
645
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
646 if (gimple_code (stmt) == GIMPLE_PHI
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
647 /* We do not process virtual PHI nodes nor do we track their
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
648 necessity. */
111
kono
parents: 67
diff changeset
649 && !virtual_operand_p (gimple_phi_result (stmt)))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
650 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
651 /* PHI nodes are somewhat special in that each PHI alternative has
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
652 data and control dependencies. All the statements feeding the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
653 PHI node's arguments are always necessary. In aggressive mode,
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
654 we also consider the control dependent edges leading to the
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
655 predecessor block associated with each PHI alternative as
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
656 necessary. */
111
kono
parents: 67
diff changeset
657 gphi *phi = as_a <gphi *> (stmt);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
658 size_t k;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
659
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
660 for (k = 0; k < gimple_phi_num_args (stmt); k++)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
661 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
662 tree arg = PHI_ARG_DEF (stmt, k);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
663 if (TREE_CODE (arg) == SSA_NAME)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
664 mark_operand_necessary (arg);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
665 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
666
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
667 /* For PHI operands it matters from where the control flow arrives
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
668 to the BB. Consider the following example:
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
669
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
670 a=exp1;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
671 b=exp2;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
672 if (test)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
673 ;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
674 else
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
675 ;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
676 c=PHI(a,b)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
677
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
678 We need to mark control dependence of the empty basic blocks, since they
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
679 contains computation of PHI operands.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
680
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
681 Doing so is too restrictive in the case the predecestor block is in
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
682 the loop. Consider:
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
683
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
684 if (b)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
685 {
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
686 int i;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
687 for (i = 0; i<1000; ++i)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
688 ;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
689 j = 0;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
690 }
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
691 return j;
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
692
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
693 There is PHI for J in the BB containing return statement.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
694 In this case the control dependence of predecestor block (that is
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
695 within the empty loop) also contains the block determining number
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
696 of iterations of the block that would prevent removing of empty
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
697 loop in this case.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
698
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
699 This scenario can be avoided by splitting critical edges.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
700 To save the critical edge splitting pass we identify how the control
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
701 dependence would look like if the edge was split.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
702
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
703 Consider the modified CFG created from current CFG by splitting
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
704 edge B->C. In the postdominance tree of modified CFG, C' is
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
705 always child of C. There are two cases how chlids of C' can look
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
706 like:
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
707
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
708 1) C' is leaf
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
709
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
710 In this case the only basic block C' is control dependent on is B.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
711
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
712 2) C' has single child that is B
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
713
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
714 In this case control dependence of C' is same as control
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
715 dependence of B in original CFG except for block B itself.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
716 (since C' postdominate B in modified CFG)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
717
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
718 Now how to decide what case happens? There are two basic options:
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
719
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
720 a) C postdominate B. Then C immediately postdominate B and
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
721 case 2 happens iff there is no other way from B to C except
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
722 the edge B->C.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
723
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
724 There is other way from B to C iff there is succesor of B that
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
725 is not postdominated by B. Testing this condition is somewhat
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
726 expensive, because we need to iterate all succesors of B.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
727 We are safe to assume that this does not happen: we will mark B
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
728 as needed when processing the other path from B to C that is
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
729 conrol dependent on B and marking control dependencies of B
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
730 itself is harmless because they will be processed anyway after
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
731 processing control statement in B.
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
732
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
733 b) C does not postdominate B. Always case 1 happens since there is
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
734 path from C to exit that does not go through B and thus also C'. */
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
735
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
736 if (aggressive && !degenerate_phi_p (stmt))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
737 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
738 for (k = 0; k < gimple_phi_num_args (stmt); k++)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
739 {
111
kono
parents: 67
diff changeset
740 basic_block arg_bb = gimple_phi_arg_edge (phi, k)->src;
63
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
741
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
742 if (gimple_bb (stmt)
b7f97abdc517 update gcc from gcc-4.5.0 to gcc-4.6
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 55
diff changeset
743 != get_immediate_dominator (CDI_POST_DOMINATORS, arg_bb))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
744 {
111
kono
parents: 67
diff changeset
745 if (!bitmap_bit_p (last_stmt_necessary, arg_bb->index))
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
746 mark_last_stmt_necessary (arg_bb);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
747 }
111
kono
parents: 67
diff changeset
748 else if (arg_bb != ENTRY_BLOCK_PTR_FOR_FN (cfun)
kono
parents: 67
diff changeset
749 && !bitmap_bit_p (visited_control_parents,
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
750 arg_bb->index))
111
kono
parents: 67
diff changeset
751 mark_control_dependent_edges_necessary (arg_bb, true);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
752 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
753 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
754 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
755 else
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
756 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
757 /* Propagate through the operands. Examine all the USE, VUSE and
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
758 VDEF operands in this statement. Mark all the statements
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
759 which feed this statement's uses as necessary. */
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
760 ssa_op_iter iter;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
761 tree use;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
762
111
kono
parents: 67
diff changeset
763 /* If this is a call to free which is directly fed by an
kono
parents: 67
diff changeset
764 allocation function do not mark that necessary through
kono
parents: 67
diff changeset
765 processing the argument. */
kono
parents: 67
diff changeset
766 if (gimple_call_builtin_p (stmt, BUILT_IN_FREE))
kono
parents: 67
diff changeset
767 {
kono
parents: 67
diff changeset
768 tree ptr = gimple_call_arg (stmt, 0);
kono
parents: 67
diff changeset
769 gimple *def_stmt;
kono
parents: 67
diff changeset
770 tree def_callee;
kono
parents: 67
diff changeset
771 /* If the pointer we free is defined by an allocation
kono
parents: 67
diff changeset
772 function do not add the call to the worklist. */
kono
parents: 67
diff changeset
773 if (TREE_CODE (ptr) == SSA_NAME
kono
parents: 67
diff changeset
774 && is_gimple_call (def_stmt = SSA_NAME_DEF_STMT (ptr))
kono
parents: 67
diff changeset
775 && (def_callee = gimple_call_fndecl (def_stmt))
kono
parents: 67
diff changeset
776 && DECL_BUILT_IN_CLASS (def_callee) == BUILT_IN_NORMAL
kono
parents: 67
diff changeset
777 && (DECL_FUNCTION_CODE (def_callee) == BUILT_IN_ALIGNED_ALLOC
kono
parents: 67
diff changeset
778 || DECL_FUNCTION_CODE (def_callee) == BUILT_IN_MALLOC
kono
parents: 67
diff changeset
779 || DECL_FUNCTION_CODE (def_callee) == BUILT_IN_CALLOC))
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
780 continue;
111
kono
parents: 67
diff changeset
781 }
kono
parents: 67
diff changeset
782
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
783 FOR_EACH_SSA_TREE_OPERAND (use, stmt, iter, SSA_OP_USE)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
784 mark_operand_necessary (use);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
785
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
786 use = gimple_vuse (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
787 if (!use)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
788 continue;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
789
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
790 /* If we dropped to simple mode make all immediately
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
791 reachable definitions necessary. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
792 if (chain_ovfl)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
793 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
794 mark_all_reaching_defs_necessary (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
795 continue;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
796 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
797
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
798 /* For statements that may load from memory (have a VUSE) we
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
799 have to mark all reaching (may-)definitions as necessary.
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
800 We partition this task into two cases:
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
801 1) explicit loads based on decls that are not aliased
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
802 2) implicit loads (like calls) and explicit loads not
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
803 based on decls that are not aliased (like indirect
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
804 references or loads from globals)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
805 For 1) we mark all reaching may-defs as necessary, stopping
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
806 at dominating kills. For 2) we want to mark all dominating
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
807 references necessary, but non-aliased ones which we handle
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
808 in 1). By keeping a global visited bitmap for references
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
809 we walk for 2) we avoid quadratic behavior for those. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
810
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
811 if (is_gimple_call (stmt))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
812 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
813 tree callee = gimple_call_fndecl (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
814 unsigned i;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
815
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
816 /* Calls to functions that are merely acting as barriers
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
817 or that only store to memory do not make any previous
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
818 stores necessary. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
819 if (callee != NULL_TREE
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
820 && DECL_BUILT_IN_CLASS (callee) == BUILT_IN_NORMAL
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
821 && (DECL_FUNCTION_CODE (callee) == BUILT_IN_MEMSET
111
kono
parents: 67
diff changeset
822 || DECL_FUNCTION_CODE (callee) == BUILT_IN_MEMSET_CHK
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
823 || DECL_FUNCTION_CODE (callee) == BUILT_IN_MALLOC
111
kono
parents: 67
diff changeset
824 || DECL_FUNCTION_CODE (callee) == BUILT_IN_ALIGNED_ALLOC
kono
parents: 67
diff changeset
825 || DECL_FUNCTION_CODE (callee) == BUILT_IN_CALLOC
kono
parents: 67
diff changeset
826 || DECL_FUNCTION_CODE (callee) == BUILT_IN_FREE
kono
parents: 67
diff changeset
827 || DECL_FUNCTION_CODE (callee) == BUILT_IN_VA_END
kono
parents: 67
diff changeset
828 || ALLOCA_FUNCTION_CODE_P (DECL_FUNCTION_CODE (callee))
kono
parents: 67
diff changeset
829 || DECL_FUNCTION_CODE (callee) == BUILT_IN_STACK_SAVE
kono
parents: 67
diff changeset
830 || DECL_FUNCTION_CODE (callee) == BUILT_IN_STACK_RESTORE
kono
parents: 67
diff changeset
831 || DECL_FUNCTION_CODE (callee) == BUILT_IN_ASSUME_ALIGNED))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
832 continue;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
833
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
834 /* Calls implicitly load from memory, their arguments
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
835 in addition may explicitly perform memory loads. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
836 mark_all_reaching_defs_necessary (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
837 for (i = 0; i < gimple_call_num_args (stmt); ++i)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
838 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
839 tree arg = gimple_call_arg (stmt, i);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
840 if (TREE_CODE (arg) == SSA_NAME
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
841 || is_gimple_min_invariant (arg))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
842 continue;
111
kono
parents: 67
diff changeset
843 if (TREE_CODE (arg) == WITH_SIZE_EXPR)
kono
parents: 67
diff changeset
844 arg = TREE_OPERAND (arg, 0);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
845 if (!ref_may_be_aliased (arg))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
846 mark_aliased_reaching_defs_necessary (stmt, arg);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
847 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
848 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
849 else if (gimple_assign_single_p (stmt))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
850 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
851 tree rhs;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
852 /* If this is a load mark things necessary. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
853 rhs = gimple_assign_rhs1 (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
854 if (TREE_CODE (rhs) != SSA_NAME
111
kono
parents: 67
diff changeset
855 && !is_gimple_min_invariant (rhs)
kono
parents: 67
diff changeset
856 && TREE_CODE (rhs) != CONSTRUCTOR)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
857 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
858 if (!ref_may_be_aliased (rhs))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
859 mark_aliased_reaching_defs_necessary (stmt, rhs);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
860 else
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
861 mark_all_reaching_defs_necessary (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
862 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
863 }
111
kono
parents: 67
diff changeset
864 else if (greturn *return_stmt = dyn_cast <greturn *> (stmt))
kono
parents: 67
diff changeset
865 {
kono
parents: 67
diff changeset
866 tree rhs = gimple_return_retval (return_stmt);
kono
parents: 67
diff changeset
867 /* A return statement may perform a load. */
kono
parents: 67
diff changeset
868 if (rhs
kono
parents: 67
diff changeset
869 && TREE_CODE (rhs) != SSA_NAME
kono
parents: 67
diff changeset
870 && !is_gimple_min_invariant (rhs)
kono
parents: 67
diff changeset
871 && TREE_CODE (rhs) != CONSTRUCTOR)
kono
parents: 67
diff changeset
872 {
kono
parents: 67
diff changeset
873 if (!ref_may_be_aliased (rhs))
kono
parents: 67
diff changeset
874 mark_aliased_reaching_defs_necessary (stmt, rhs);
kono
parents: 67
diff changeset
875 else
kono
parents: 67
diff changeset
876 mark_all_reaching_defs_necessary (stmt);
kono
parents: 67
diff changeset
877 }
kono
parents: 67
diff changeset
878 }
kono
parents: 67
diff changeset
879 else if (gasm *asm_stmt = dyn_cast <gasm *> (stmt))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
880 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
881 unsigned i;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
882 mark_all_reaching_defs_necessary (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
883 /* Inputs may perform loads. */
111
kono
parents: 67
diff changeset
884 for (i = 0; i < gimple_asm_ninputs (asm_stmt); ++i)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
885 {
111
kono
parents: 67
diff changeset
886 tree op = TREE_VALUE (gimple_asm_input_op (asm_stmt, i));
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
887 if (TREE_CODE (op) != SSA_NAME
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
888 && !is_gimple_min_invariant (op)
111
kono
parents: 67
diff changeset
889 && TREE_CODE (op) != CONSTRUCTOR
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
890 && !ref_may_be_aliased (op))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
891 mark_aliased_reaching_defs_necessary (stmt, op);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
892 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
893 }
111
kono
parents: 67
diff changeset
894 else if (gimple_code (stmt) == GIMPLE_TRANSACTION)
kono
parents: 67
diff changeset
895 {
kono
parents: 67
diff changeset
896 /* The beginning of a transaction is a memory barrier. */
kono
parents: 67
diff changeset
897 /* ??? If we were really cool, we'd only be a barrier
kono
parents: 67
diff changeset
898 for the memories touched within the transaction. */
kono
parents: 67
diff changeset
899 mark_all_reaching_defs_necessary (stmt);
kono
parents: 67
diff changeset
900 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
901 else
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
902 gcc_unreachable ();
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
903
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
904 /* If we over-used our alias oracle budget drop to simple
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
905 mode. The cost metric allows quadratic behavior
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
906 (number of uses times number of may-defs queries) up to
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
907 a constant maximal number of queries and after that falls back to
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
908 super-linear complexity. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
909 if (/* Constant but quadratic for small functions. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
910 total_chain > 128 * 128
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
911 /* Linear in the number of may-defs. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
912 && total_chain > 32 * longest_chain
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
913 /* Linear in the number of uses. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
914 && total_chain > nr_walks * 32)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
915 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
916 chain_ovfl = true;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
917 if (visited)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
918 bitmap_clear (visited);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
919 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
920 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
921 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
922 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
923
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
924 /* Remove dead PHI nodes from block BB. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
925
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
926 static bool
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
927 remove_dead_phis (basic_block bb)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
928 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
929 bool something_changed = false;
111
kono
parents: 67
diff changeset
930 gphi *phi;
kono
parents: 67
diff changeset
931 gphi_iterator gsi;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
932
111
kono
parents: 67
diff changeset
933 for (gsi = gsi_start_phis (bb); !gsi_end_p (gsi);)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
934 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
935 stats.total_phis++;
111
kono
parents: 67
diff changeset
936 phi = gsi.phi ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
937
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
938 /* We do not track necessity of virtual PHI nodes. Instead do
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
939 very simple dead PHI removal here. */
111
kono
parents: 67
diff changeset
940 if (virtual_operand_p (gimple_phi_result (phi)))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
941 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
942 /* Virtual PHI nodes with one or identical arguments
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
943 can be removed. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
944 if (degenerate_phi_p (phi))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
945 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
946 tree vdef = gimple_phi_result (phi);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
947 tree vuse = gimple_phi_arg_def (phi, 0);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
948
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
949 use_operand_p use_p;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
950 imm_use_iterator iter;
111
kono
parents: 67
diff changeset
951 gimple *use_stmt;
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
952 FOR_EACH_IMM_USE_STMT (use_stmt, iter, vdef)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
953 FOR_EACH_IMM_USE_ON_STMT (use_p, iter)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
954 SET_USE (use_p, vuse);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
955 if (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (vdef)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
956 && TREE_CODE (vuse) == SSA_NAME)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
957 SSA_NAME_OCCURS_IN_ABNORMAL_PHI (vuse) = 1;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
958 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
959 else
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
960 gimple_set_plf (phi, STMT_NECESSARY, true);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
961 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
962
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
963 if (!gimple_plf (phi, STMT_NECESSARY))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
964 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
965 something_changed = true;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
966 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
967 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
968 fprintf (dump_file, "Deleting : ");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
969 print_gimple_stmt (dump_file, phi, 0, TDF_SLIM);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
970 fprintf (dump_file, "\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
971 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
972
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
973 remove_phi_node (&gsi, true);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
974 stats.removed_phis++;
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
975 continue;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
976 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
977
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
978 gsi_next (&gsi);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
979 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
980 return something_changed;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
981 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
982
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
983
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
984 /* Remove dead statement pointed to by iterator I. Receives the basic block BB
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
985 containing I so that we don't have to look it up. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
986
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
987 static void
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
988 remove_dead_stmt (gimple_stmt_iterator *i, basic_block bb)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
989 {
111
kono
parents: 67
diff changeset
990 gimple *stmt = gsi_stmt (*i);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
991
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
992 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
993 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
994 fprintf (dump_file, "Deleting : ");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
995 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
996 fprintf (dump_file, "\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
997 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
998
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
999 stats.removed++;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1000
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1001 /* If we have determined that a conditional branch statement contributes
111
kono
parents: 67
diff changeset
1002 nothing to the program, then we not only remove it, but we need to update
kono
parents: 67
diff changeset
1003 the CFG. We can chose any of edges out of BB as long as we are sure to not
kono
parents: 67
diff changeset
1004 close infinite loops. This is done by always choosing the edge closer to
kono
parents: 67
diff changeset
1005 exit in inverted_post_order_compute order. */
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1006 if (is_ctrl_stmt (stmt))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1007 {
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1008 edge_iterator ei;
111
kono
parents: 67
diff changeset
1009 edge e = NULL, e2;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1010
111
kono
parents: 67
diff changeset
1011 /* See if there is only one non-abnormal edge. */
kono
parents: 67
diff changeset
1012 if (single_succ_p (bb))
kono
parents: 67
diff changeset
1013 e = single_succ_edge (bb);
kono
parents: 67
diff changeset
1014 /* Otherwise chose one that is closer to bb with live statement in it.
kono
parents: 67
diff changeset
1015 To be able to chose one, we compute inverted post order starting from
kono
parents: 67
diff changeset
1016 all BBs with live statements. */
kono
parents: 67
diff changeset
1017 if (!e)
kono
parents: 67
diff changeset
1018 {
kono
parents: 67
diff changeset
1019 if (!bb_postorder)
kono
parents: 67
diff changeset
1020 {
kono
parents: 67
diff changeset
1021 auto_vec<int, 20> postorder;
kono
parents: 67
diff changeset
1022 inverted_post_order_compute (&postorder,
kono
parents: 67
diff changeset
1023 &bb_contains_live_stmts);
kono
parents: 67
diff changeset
1024 bb_postorder = XNEWVEC (int, last_basic_block_for_fn (cfun));
kono
parents: 67
diff changeset
1025 for (unsigned int i = 0; i < postorder.length (); ++i)
kono
parents: 67
diff changeset
1026 bb_postorder[postorder[i]] = i;
kono
parents: 67
diff changeset
1027 }
kono
parents: 67
diff changeset
1028 FOR_EACH_EDGE (e2, ei, bb->succs)
kono
parents: 67
diff changeset
1029 if (!e || e2->dest == EXIT_BLOCK_PTR_FOR_FN (cfun)
kono
parents: 67
diff changeset
1030 || bb_postorder [e->dest->index]
kono
parents: 67
diff changeset
1031 < bb_postorder [e2->dest->index])
kono
parents: 67
diff changeset
1032 e = e2;
kono
parents: 67
diff changeset
1033 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1034 gcc_assert (e);
111
kono
parents: 67
diff changeset
1035 e->probability = profile_probability::always ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1036
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1037 /* The edge is no longer associated with a conditional, so it does
111
kono
parents: 67
diff changeset
1038 not have TRUE/FALSE flags.
kono
parents: 67
diff changeset
1039 We are also safe to drop EH/ABNORMAL flags and turn them into
kono
parents: 67
diff changeset
1040 normal control flow, because we know that all the destinations (including
kono
parents: 67
diff changeset
1041 those odd edges) are equivalent for program execution. */
kono
parents: 67
diff changeset
1042 e->flags &= ~(EDGE_TRUE_VALUE | EDGE_FALSE_VALUE | EDGE_EH | EDGE_ABNORMAL);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1043
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1044 /* The lone outgoing edge from BB will be a fallthru edge. */
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1045 e->flags |= EDGE_FALLTHRU;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1046
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1047 /* Remove the remaining outgoing edges. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1048 for (ei = ei_start (bb->succs); (e2 = ei_safe_edge (ei)); )
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1049 if (e != e2)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1050 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1051 cfg_altered = true;
111
kono
parents: 67
diff changeset
1052 /* If we made a BB unconditionally exit a loop or removed
kono
parents: 67
diff changeset
1053 an entry into an irreducible region, then this transform
kono
parents: 67
diff changeset
1054 alters the set of BBs in the loop. Schedule a fixup. */
kono
parents: 67
diff changeset
1055 if (loop_exit_edge_p (bb->loop_father, e)
kono
parents: 67
diff changeset
1056 || (e2->dest->flags & BB_IRREDUCIBLE_LOOP))
kono
parents: 67
diff changeset
1057 loops_state_set (LOOPS_NEED_FIXUP);
kono
parents: 67
diff changeset
1058 remove_edge (e2);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1059 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1060 else
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1061 ei_next (&ei);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1062 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1063
111
kono
parents: 67
diff changeset
1064 /* If this is a store into a variable that is being optimized away,
kono
parents: 67
diff changeset
1065 add a debug bind stmt if possible. */
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1066 if (MAY_HAVE_DEBUG_BIND_STMTS
111
kono
parents: 67
diff changeset
1067 && gimple_assign_single_p (stmt)
kono
parents: 67
diff changeset
1068 && is_gimple_val (gimple_assign_rhs1 (stmt)))
kono
parents: 67
diff changeset
1069 {
kono
parents: 67
diff changeset
1070 tree lhs = gimple_assign_lhs (stmt);
kono
parents: 67
diff changeset
1071 if ((VAR_P (lhs) || TREE_CODE (lhs) == PARM_DECL)
kono
parents: 67
diff changeset
1072 && !DECL_IGNORED_P (lhs)
kono
parents: 67
diff changeset
1073 && is_gimple_reg_type (TREE_TYPE (lhs))
kono
parents: 67
diff changeset
1074 && !is_global_var (lhs)
kono
parents: 67
diff changeset
1075 && !DECL_HAS_VALUE_EXPR_P (lhs))
kono
parents: 67
diff changeset
1076 {
kono
parents: 67
diff changeset
1077 tree rhs = gimple_assign_rhs1 (stmt);
kono
parents: 67
diff changeset
1078 gdebug *note
kono
parents: 67
diff changeset
1079 = gimple_build_debug_bind (lhs, unshare_expr (rhs), stmt);
kono
parents: 67
diff changeset
1080 gsi_insert_after (i, note, GSI_SAME_STMT);
kono
parents: 67
diff changeset
1081 }
kono
parents: 67
diff changeset
1082 }
kono
parents: 67
diff changeset
1083
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1084 unlink_stmt_vdef (stmt);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1085 gsi_remove (i, true);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1086 release_defs (stmt);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1087 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1088
111
kono
parents: 67
diff changeset
1089 /* Helper for maybe_optimize_arith_overflow. Find in *TP if there are any
kono
parents: 67
diff changeset
1090 uses of data (SSA_NAME) other than REALPART_EXPR referencing it. */
kono
parents: 67
diff changeset
1091
kono
parents: 67
diff changeset
1092 static tree
kono
parents: 67
diff changeset
1093 find_non_realpart_uses (tree *tp, int *walk_subtrees, void *data)
kono
parents: 67
diff changeset
1094 {
kono
parents: 67
diff changeset
1095 if (TYPE_P (*tp) || TREE_CODE (*tp) == REALPART_EXPR)
kono
parents: 67
diff changeset
1096 *walk_subtrees = 0;
kono
parents: 67
diff changeset
1097 if (*tp == (tree) data)
kono
parents: 67
diff changeset
1098 return *tp;
kono
parents: 67
diff changeset
1099 return NULL_TREE;
kono
parents: 67
diff changeset
1100 }
kono
parents: 67
diff changeset
1101
kono
parents: 67
diff changeset
1102 /* If the IMAGPART_EXPR of the {ADD,SUB,MUL}_OVERFLOW result is never used,
kono
parents: 67
diff changeset
1103 but REALPART_EXPR is, optimize the {ADD,SUB,MUL}_OVERFLOW internal calls
kono
parents: 67
diff changeset
1104 into plain unsigned {PLUS,MINUS,MULT}_EXPR, and if needed reset debug
kono
parents: 67
diff changeset
1105 uses. */
kono
parents: 67
diff changeset
1106
kono
parents: 67
diff changeset
1107 static void
kono
parents: 67
diff changeset
1108 maybe_optimize_arith_overflow (gimple_stmt_iterator *gsi,
kono
parents: 67
diff changeset
1109 enum tree_code subcode)
kono
parents: 67
diff changeset
1110 {
kono
parents: 67
diff changeset
1111 gimple *stmt = gsi_stmt (*gsi);
kono
parents: 67
diff changeset
1112 tree lhs = gimple_call_lhs (stmt);
kono
parents: 67
diff changeset
1113
kono
parents: 67
diff changeset
1114 if (lhs == NULL || TREE_CODE (lhs) != SSA_NAME)
kono
parents: 67
diff changeset
1115 return;
kono
parents: 67
diff changeset
1116
kono
parents: 67
diff changeset
1117 imm_use_iterator imm_iter;
kono
parents: 67
diff changeset
1118 use_operand_p use_p;
kono
parents: 67
diff changeset
1119 bool has_debug_uses = false;
kono
parents: 67
diff changeset
1120 bool has_realpart_uses = false;
kono
parents: 67
diff changeset
1121 bool has_other_uses = false;
kono
parents: 67
diff changeset
1122 FOR_EACH_IMM_USE_FAST (use_p, imm_iter, lhs)
kono
parents: 67
diff changeset
1123 {
kono
parents: 67
diff changeset
1124 gimple *use_stmt = USE_STMT (use_p);
kono
parents: 67
diff changeset
1125 if (is_gimple_debug (use_stmt))
kono
parents: 67
diff changeset
1126 has_debug_uses = true;
kono
parents: 67
diff changeset
1127 else if (is_gimple_assign (use_stmt)
kono
parents: 67
diff changeset
1128 && gimple_assign_rhs_code (use_stmt) == REALPART_EXPR
kono
parents: 67
diff changeset
1129 && TREE_OPERAND (gimple_assign_rhs1 (use_stmt), 0) == lhs)
kono
parents: 67
diff changeset
1130 has_realpart_uses = true;
kono
parents: 67
diff changeset
1131 else
kono
parents: 67
diff changeset
1132 {
kono
parents: 67
diff changeset
1133 has_other_uses = true;
kono
parents: 67
diff changeset
1134 break;
kono
parents: 67
diff changeset
1135 }
kono
parents: 67
diff changeset
1136 }
kono
parents: 67
diff changeset
1137
kono
parents: 67
diff changeset
1138 if (!has_realpart_uses || has_other_uses)
kono
parents: 67
diff changeset
1139 return;
kono
parents: 67
diff changeset
1140
kono
parents: 67
diff changeset
1141 tree arg0 = gimple_call_arg (stmt, 0);
kono
parents: 67
diff changeset
1142 tree arg1 = gimple_call_arg (stmt, 1);
kono
parents: 67
diff changeset
1143 location_t loc = gimple_location (stmt);
kono
parents: 67
diff changeset
1144 tree type = TREE_TYPE (TREE_TYPE (lhs));
kono
parents: 67
diff changeset
1145 tree utype = type;
kono
parents: 67
diff changeset
1146 if (!TYPE_UNSIGNED (type))
kono
parents: 67
diff changeset
1147 utype = build_nonstandard_integer_type (TYPE_PRECISION (type), 1);
kono
parents: 67
diff changeset
1148 tree result = fold_build2_loc (loc, subcode, utype,
kono
parents: 67
diff changeset
1149 fold_convert_loc (loc, utype, arg0),
kono
parents: 67
diff changeset
1150 fold_convert_loc (loc, utype, arg1));
kono
parents: 67
diff changeset
1151 result = fold_convert_loc (loc, type, result);
kono
parents: 67
diff changeset
1152
kono
parents: 67
diff changeset
1153 if (has_debug_uses)
kono
parents: 67
diff changeset
1154 {
kono
parents: 67
diff changeset
1155 gimple *use_stmt;
kono
parents: 67
diff changeset
1156 FOR_EACH_IMM_USE_STMT (use_stmt, imm_iter, lhs)
kono
parents: 67
diff changeset
1157 {
kono
parents: 67
diff changeset
1158 if (!gimple_debug_bind_p (use_stmt))
kono
parents: 67
diff changeset
1159 continue;
kono
parents: 67
diff changeset
1160 tree v = gimple_debug_bind_get_value (use_stmt);
kono
parents: 67
diff changeset
1161 if (walk_tree (&v, find_non_realpart_uses, lhs, NULL))
kono
parents: 67
diff changeset
1162 {
kono
parents: 67
diff changeset
1163 gimple_debug_bind_reset_value (use_stmt);
kono
parents: 67
diff changeset
1164 update_stmt (use_stmt);
kono
parents: 67
diff changeset
1165 }
kono
parents: 67
diff changeset
1166 }
kono
parents: 67
diff changeset
1167 }
kono
parents: 67
diff changeset
1168
kono
parents: 67
diff changeset
1169 if (TREE_CODE (result) == INTEGER_CST && TREE_OVERFLOW (result))
kono
parents: 67
diff changeset
1170 result = drop_tree_overflow (result);
kono
parents: 67
diff changeset
1171 tree overflow = build_zero_cst (type);
kono
parents: 67
diff changeset
1172 tree ctype = build_complex_type (type);
kono
parents: 67
diff changeset
1173 if (TREE_CODE (result) == INTEGER_CST)
kono
parents: 67
diff changeset
1174 result = build_complex (ctype, result, overflow);
kono
parents: 67
diff changeset
1175 else
kono
parents: 67
diff changeset
1176 result = build2_loc (gimple_location (stmt), COMPLEX_EXPR,
kono
parents: 67
diff changeset
1177 ctype, result, overflow);
kono
parents: 67
diff changeset
1178
kono
parents: 67
diff changeset
1179 if (dump_file && (dump_flags & TDF_DETAILS))
kono
parents: 67
diff changeset
1180 {
kono
parents: 67
diff changeset
1181 fprintf (dump_file, "Transforming call: ");
kono
parents: 67
diff changeset
1182 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
kono
parents: 67
diff changeset
1183 fprintf (dump_file, "because the overflow result is never used into: ");
kono
parents: 67
diff changeset
1184 print_generic_stmt (dump_file, result, TDF_SLIM);
kono
parents: 67
diff changeset
1185 fprintf (dump_file, "\n");
kono
parents: 67
diff changeset
1186 }
kono
parents: 67
diff changeset
1187
kono
parents: 67
diff changeset
1188 if (!update_call_from_tree (gsi, result))
kono
parents: 67
diff changeset
1189 gimplify_and_update_call_from_tree (gsi, result);
kono
parents: 67
diff changeset
1190 }
kono
parents: 67
diff changeset
1191
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1192 /* Eliminate unnecessary statements. Any instruction not marked as necessary
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1193 contributes nothing to the program, and can be deleted. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1194
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1195 static bool
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1196 eliminate_unnecessary_stmts (void)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1197 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1198 bool something_changed = false;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1199 basic_block bb;
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1200 gimple_stmt_iterator gsi, psi;
111
kono
parents: 67
diff changeset
1201 gimple *stmt;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1202 tree call;
111
kono
parents: 67
diff changeset
1203 vec<basic_block> h;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1204
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1205 if (dump_file && (dump_flags & TDF_DETAILS))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1206 fprintf (dump_file, "\nEliminating unnecessary statements:\n");
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1207
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1208 clear_special_calls ();
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1209
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1210 /* Walking basic blocks and statements in reverse order avoids
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1211 releasing SSA names before any other DEFs that refer to them are
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1212 released. This helps avoid loss of debug information, as we get
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1213 a chance to propagate all RHSs of removed SSAs into debug uses,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1214 rather than only the latest ones. E.g., consider:
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1215
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1216 x_3 = y_1 + z_2;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1217 a_5 = x_3 - b_4;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1218 # DEBUG a => a_5
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1219
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1220 If we were to release x_3 before a_5, when we reached a_5 and
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1221 tried to substitute it into the debug stmt, we'd see x_3 there,
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1222 but x_3's DEF, type, etc would have already been disconnected.
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1223 By going backwards, the debug stmt first changes to:
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1224
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1225 # DEBUG a => x_3 - b_4
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1226
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1227 and then to:
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1228
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1229 # DEBUG a => y_1 + z_2 - b_4
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1230
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1231 as desired. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1232 gcc_assert (dom_info_available_p (CDI_DOMINATORS));
111
kono
parents: 67
diff changeset
1233 h = get_all_dominated_blocks (CDI_DOMINATORS,
kono
parents: 67
diff changeset
1234 single_succ (ENTRY_BLOCK_PTR_FOR_FN (cfun)));
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1235
111
kono
parents: 67
diff changeset
1236 while (h.length ())
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1237 {
111
kono
parents: 67
diff changeset
1238 bb = h.pop ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1239
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1240 /* Remove dead statements. */
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1241 for (gsi = gsi_last_bb (bb); !gsi_end_p (gsi); gsi = psi)
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1242 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1243 stmt = gsi_stmt (gsi);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1244
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1245 psi = gsi;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1246 gsi_prev (&psi);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1247
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1248 stats.total++;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1249
111
kono
parents: 67
diff changeset
1250 /* We can mark a call to free as not necessary if the
kono
parents: 67
diff changeset
1251 defining statement of its argument is not necessary
kono
parents: 67
diff changeset
1252 (and thus is getting removed). */
kono
parents: 67
diff changeset
1253 if (gimple_plf (stmt, STMT_NECESSARY)
kono
parents: 67
diff changeset
1254 && gimple_call_builtin_p (stmt, BUILT_IN_FREE))
kono
parents: 67
diff changeset
1255 {
kono
parents: 67
diff changeset
1256 tree ptr = gimple_call_arg (stmt, 0);
kono
parents: 67
diff changeset
1257 if (TREE_CODE (ptr) == SSA_NAME)
kono
parents: 67
diff changeset
1258 {
kono
parents: 67
diff changeset
1259 gimple *def_stmt = SSA_NAME_DEF_STMT (ptr);
kono
parents: 67
diff changeset
1260 if (!gimple_nop_p (def_stmt)
kono
parents: 67
diff changeset
1261 && !gimple_plf (def_stmt, STMT_NECESSARY))
kono
parents: 67
diff changeset
1262 gimple_set_plf (stmt, STMT_NECESSARY, false);
kono
parents: 67
diff changeset
1263 }
kono
parents: 67
diff changeset
1264 }
kono
parents: 67
diff changeset
1265
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1266 /* If GSI is not necessary then remove it. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1267 if (!gimple_plf (stmt, STMT_NECESSARY))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1268 {
111
kono
parents: 67
diff changeset
1269 /* Keep clobbers that we can keep live live. */
kono
parents: 67
diff changeset
1270 if (gimple_clobber_p (stmt))
kono
parents: 67
diff changeset
1271 {
kono
parents: 67
diff changeset
1272 ssa_op_iter iter;
kono
parents: 67
diff changeset
1273 use_operand_p use_p;
kono
parents: 67
diff changeset
1274 bool dead = false;
kono
parents: 67
diff changeset
1275 FOR_EACH_SSA_USE_OPERAND (use_p, stmt, iter, SSA_OP_USE)
kono
parents: 67
diff changeset
1276 {
kono
parents: 67
diff changeset
1277 tree name = USE_FROM_PTR (use_p);
kono
parents: 67
diff changeset
1278 if (!SSA_NAME_IS_DEFAULT_DEF (name)
kono
parents: 67
diff changeset
1279 && !bitmap_bit_p (processed, SSA_NAME_VERSION (name)))
kono
parents: 67
diff changeset
1280 {
kono
parents: 67
diff changeset
1281 dead = true;
kono
parents: 67
diff changeset
1282 break;
kono
parents: 67
diff changeset
1283 }
kono
parents: 67
diff changeset
1284 }
kono
parents: 67
diff changeset
1285 if (!dead)
kono
parents: 67
diff changeset
1286 continue;
kono
parents: 67
diff changeset
1287 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1288 if (!is_gimple_debug (stmt))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1289 something_changed = true;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1290 remove_dead_stmt (&gsi, bb);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1291 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1292 else if (is_gimple_call (stmt))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1293 {
111
kono
parents: 67
diff changeset
1294 tree name = gimple_call_lhs (stmt);
kono
parents: 67
diff changeset
1295
kono
parents: 67
diff changeset
1296 notice_special_calls (as_a <gcall *> (stmt));
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1297
111
kono
parents: 67
diff changeset
1298 /* When LHS of var = call (); is dead, simplify it into
kono
parents: 67
diff changeset
1299 call (); saving one operand. */
kono
parents: 67
diff changeset
1300 if (name
kono
parents: 67
diff changeset
1301 && TREE_CODE (name) == SSA_NAME
kono
parents: 67
diff changeset
1302 && !bitmap_bit_p (processed, SSA_NAME_VERSION (name))
kono
parents: 67
diff changeset
1303 /* Avoid doing so for allocation calls which we
kono
parents: 67
diff changeset
1304 did not mark as necessary, it will confuse the
kono
parents: 67
diff changeset
1305 special logic we apply to malloc/free pair removal. */
kono
parents: 67
diff changeset
1306 && (!(call = gimple_call_fndecl (stmt))
kono
parents: 67
diff changeset
1307 || DECL_BUILT_IN_CLASS (call) != BUILT_IN_NORMAL
kono
parents: 67
diff changeset
1308 || (DECL_FUNCTION_CODE (call) != BUILT_IN_ALIGNED_ALLOC
kono
parents: 67
diff changeset
1309 && DECL_FUNCTION_CODE (call) != BUILT_IN_MALLOC
kono
parents: 67
diff changeset
1310 && DECL_FUNCTION_CODE (call) != BUILT_IN_CALLOC
kono
parents: 67
diff changeset
1311 && !ALLOCA_FUNCTION_CODE_P
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1312 (DECL_FUNCTION_CODE (call)))))
111
kono
parents: 67
diff changeset
1313 {
kono
parents: 67
diff changeset
1314 something_changed = true;
kono
parents: 67
diff changeset
1315 if (dump_file && (dump_flags & TDF_DETAILS))
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1316 {
111
kono
parents: 67
diff changeset
1317 fprintf (dump_file, "Deleting LHS of call: ");
kono
parents: 67
diff changeset
1318 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
kono
parents: 67
diff changeset
1319 fprintf (dump_file, "\n");
kono
parents: 67
diff changeset
1320 }
kono
parents: 67
diff changeset
1321
kono
parents: 67
diff changeset
1322 gimple_call_set_lhs (stmt, NULL_TREE);
kono
parents: 67
diff changeset
1323 maybe_clean_or_replace_eh_stmt (stmt, stmt);
kono
parents: 67
diff changeset
1324 update_stmt (stmt);
kono
parents: 67
diff changeset
1325 release_ssa_name (name);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1326
111
kono
parents: 67
diff changeset
1327 /* GOMP_SIMD_LANE or ASAN_POISON without lhs is not
kono
parents: 67
diff changeset
1328 needed. */
kono
parents: 67
diff changeset
1329 if (gimple_call_internal_p (stmt))
kono
parents: 67
diff changeset
1330 switch (gimple_call_internal_fn (stmt))
kono
parents: 67
diff changeset
1331 {
kono
parents: 67
diff changeset
1332 case IFN_GOMP_SIMD_LANE:
kono
parents: 67
diff changeset
1333 case IFN_ASAN_POISON:
kono
parents: 67
diff changeset
1334 remove_dead_stmt (&gsi, bb);
kono
parents: 67
diff changeset
1335 break;
kono
parents: 67
diff changeset
1336 default:
kono
parents: 67
diff changeset
1337 break;
kono
parents: 67
diff changeset
1338 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1339 }
111
kono
parents: 67
diff changeset
1340 else if (gimple_call_internal_p (stmt))
kono
parents: 67
diff changeset
1341 switch (gimple_call_internal_fn (stmt))
kono
parents: 67
diff changeset
1342 {
kono
parents: 67
diff changeset
1343 case IFN_ADD_OVERFLOW:
kono
parents: 67
diff changeset
1344 maybe_optimize_arith_overflow (&gsi, PLUS_EXPR);
kono
parents: 67
diff changeset
1345 break;
kono
parents: 67
diff changeset
1346 case IFN_SUB_OVERFLOW:
kono
parents: 67
diff changeset
1347 maybe_optimize_arith_overflow (&gsi, MINUS_EXPR);
kono
parents: 67
diff changeset
1348 break;
kono
parents: 67
diff changeset
1349 case IFN_MUL_OVERFLOW:
kono
parents: 67
diff changeset
1350 maybe_optimize_arith_overflow (&gsi, MULT_EXPR);
kono
parents: 67
diff changeset
1351 break;
kono
parents: 67
diff changeset
1352 default:
kono
parents: 67
diff changeset
1353 break;
kono
parents: 67
diff changeset
1354 }
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1355 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1356 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1357 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1358
111
kono
parents: 67
diff changeset
1359 h.release ();
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1360
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1361 /* Since we don't track liveness of virtual PHI nodes, it is possible that we
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1362 rendered some PHI nodes unreachable while they are still in use.
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1363 Mark them for renaming. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1364 if (cfg_altered)
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1365 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1366 basic_block prev_bb;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1367
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1368 find_unreachable_blocks ();
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1369
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1370 /* Delete all unreachable basic blocks in reverse dominator order. */
111
kono
parents: 67
diff changeset
1371 for (bb = EXIT_BLOCK_PTR_FOR_FN (cfun)->prev_bb;
kono
parents: 67
diff changeset
1372 bb != ENTRY_BLOCK_PTR_FOR_FN (cfun); bb = prev_bb)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1373 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1374 prev_bb = bb->prev_bb;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1375
111
kono
parents: 67
diff changeset
1376 if (!bitmap_bit_p (bb_contains_live_stmts, bb->index)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1377 || !(bb->flags & BB_REACHABLE))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1378 {
111
kono
parents: 67
diff changeset
1379 for (gphi_iterator gsi = gsi_start_phis (bb); !gsi_end_p (gsi);
kono
parents: 67
diff changeset
1380 gsi_next (&gsi))
kono
parents: 67
diff changeset
1381 if (virtual_operand_p (gimple_phi_result (gsi.phi ())))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1382 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1383 bool found = false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1384 imm_use_iterator iter;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1385
111
kono
parents: 67
diff changeset
1386 FOR_EACH_IMM_USE_STMT (stmt, iter,
kono
parents: 67
diff changeset
1387 gimple_phi_result (gsi.phi ()))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1388 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1389 if (!(gimple_bb (stmt)->flags & BB_REACHABLE))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1390 continue;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1391 if (gimple_code (stmt) == GIMPLE_PHI
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1392 || gimple_plf (stmt, STMT_NECESSARY))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1393 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1394 found = true;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1395 BREAK_FROM_IMM_USE_STMT (iter);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1396 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1397 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1398 if (found)
111
kono
parents: 67
diff changeset
1399 mark_virtual_phi_result_for_renaming (gsi.phi ());
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1400 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1401
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1402 if (!(bb->flags & BB_REACHABLE))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1403 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1404 /* Speed up the removal of blocks that don't
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1405 dominate others. Walking backwards, this should
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1406 be the common case. ??? Do we need to recompute
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1407 dominators because of cfg_altered? */
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1408 if (!first_dom_son (CDI_DOMINATORS, bb))
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1409 delete_basic_block (bb);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1410 else
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1411 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1412 h = get_all_dominated_blocks (CDI_DOMINATORS, bb);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1413
111
kono
parents: 67
diff changeset
1414 while (h.length ())
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1415 {
111
kono
parents: 67
diff changeset
1416 bb = h.pop ();
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1417 prev_bb = bb->prev_bb;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1418 /* Rearrangements to the CFG may have failed
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1419 to update the dominators tree, so that
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1420 formerly-dominated blocks are now
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1421 otherwise reachable. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1422 if (!!(bb->flags & BB_REACHABLE))
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1423 continue;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1424 delete_basic_block (bb);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1425 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1426
111
kono
parents: 67
diff changeset
1427 h.release ();
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1428 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1429 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1430 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1431 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1432 }
111
kono
parents: 67
diff changeset
1433 FOR_EACH_BB_FN (bb, cfun)
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1434 {
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1435 /* Remove dead PHI nodes. */
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1436 something_changed |= remove_dead_phis (bb);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1437 }
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1438
111
kono
parents: 67
diff changeset
1439 if (bb_postorder)
kono
parents: 67
diff changeset
1440 free (bb_postorder);
kono
parents: 67
diff changeset
1441 bb_postorder = NULL;
kono
parents: 67
diff changeset
1442
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1443 return something_changed;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1444 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1445
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1446
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1447 /* Print out removed statement statistics. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1448
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1449 static void
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1450 print_stats (void)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1451 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1452 float percg;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1453
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1454 percg = ((float) stats.removed / (float) stats.total) * 100;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1455 fprintf (dump_file, "Removed %d of %d statements (%d%%)\n",
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1456 stats.removed, stats.total, (int) percg);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1457
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1458 if (stats.total_phis == 0)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1459 percg = 0;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1460 else
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1461 percg = ((float) stats.removed_phis / (float) stats.total_phis) * 100;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1462
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1463 fprintf (dump_file, "Removed %d of %d PHI nodes (%d%%)\n",
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1464 stats.removed_phis, stats.total_phis, (int) percg);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1465 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1466
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1467 /* Initialization for this pass. Set up the used data structures. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1468
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1469 static void
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1470 tree_dce_init (bool aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1471 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1472 memset ((void *) &stats, 0, sizeof (stats));
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1473
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1474 if (aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1475 {
111
kono
parents: 67
diff changeset
1476 last_stmt_necessary = sbitmap_alloc (last_basic_block_for_fn (cfun));
kono
parents: 67
diff changeset
1477 bitmap_clear (last_stmt_necessary);
kono
parents: 67
diff changeset
1478 bb_contains_live_stmts = sbitmap_alloc (last_basic_block_for_fn (cfun));
kono
parents: 67
diff changeset
1479 bitmap_clear (bb_contains_live_stmts);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1480 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1481
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1482 processed = sbitmap_alloc (num_ssa_names + 1);
111
kono
parents: 67
diff changeset
1483 bitmap_clear (processed);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1484
111
kono
parents: 67
diff changeset
1485 worklist.create (64);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1486 cfg_altered = false;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1487 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1488
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1489 /* Cleanup after this pass. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1490
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1491 static void
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1492 tree_dce_done (bool aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1493 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1494 if (aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1495 {
111
kono
parents: 67
diff changeset
1496 delete cd;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1497 sbitmap_free (visited_control_parents);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1498 sbitmap_free (last_stmt_necessary);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1499 sbitmap_free (bb_contains_live_stmts);
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1500 bb_contains_live_stmts = NULL;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1501 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1502
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1503 sbitmap_free (processed);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1504
111
kono
parents: 67
diff changeset
1505 worklist.release ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1506 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1507
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1508 /* Main routine to eliminate dead code.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1509
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1510 AGGRESSIVE controls the aggressiveness of the algorithm.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1511 In conservative mode, we ignore control dependence and simply declare
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1512 all but the most trivially dead branches necessary. This mode is fast.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1513 In aggressive mode, control dependences are taken into account, which
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1514 results in more dead code elimination, but at the cost of some time.
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1515
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1516 FIXME: Aggressive mode before PRE doesn't work currently because
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1517 the dominance info is not invalidated after DCE1. This is
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1518 not an issue right now because we only run aggressive DCE
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1519 as the last tree SSA pass, but keep this in mind when you
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1520 start experimenting with pass ordering. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1521
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1522 static unsigned int
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1523 perform_tree_ssa_dce (bool aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1524 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1525 bool something_changed = 0;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1526
67
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
1527 calculate_dominance_info (CDI_DOMINATORS);
f6334be47118 update gcc from gcc-4.6-20100522 to gcc-4.6-20110318
nobuyasu <dimolto@cr.ie.u-ryukyu.ac.jp>
parents: 63
diff changeset
1528
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1529 /* Preheaders are needed for SCEV to work.
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1530 Simple lateches and recorded exits improve chances that loop will
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1531 proved to be finite in testcases such as in loop-15.c and loop-24.c */
111
kono
parents: 67
diff changeset
1532 bool in_loop_pipeline = scev_initialized_p ();
kono
parents: 67
diff changeset
1533 if (aggressive && ! in_loop_pipeline)
kono
parents: 67
diff changeset
1534 {
kono
parents: 67
diff changeset
1535 scev_initialize ();
kono
parents: 67
diff changeset
1536 loop_optimizer_init (LOOPS_NORMAL
kono
parents: 67
diff changeset
1537 | LOOPS_HAVE_RECORDED_EXITS);
kono
parents: 67
diff changeset
1538 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1539
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1540 tree_dce_init (aggressive);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1541
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1542 if (aggressive)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1543 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1544 /* Compute control dependence. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1545 calculate_dominance_info (CDI_POST_DOMINATORS);
111
kono
parents: 67
diff changeset
1546 cd = new control_dependences ();
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1547
111
kono
parents: 67
diff changeset
1548 visited_control_parents =
kono
parents: 67
diff changeset
1549 sbitmap_alloc (last_basic_block_for_fn (cfun));
kono
parents: 67
diff changeset
1550 bitmap_clear (visited_control_parents);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1551
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1552 mark_dfs_back_edges ();
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1553 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1554
111
kono
parents: 67
diff changeset
1555 find_obviously_necessary_stmts (aggressive);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1556
111
kono
parents: 67
diff changeset
1557 if (aggressive && ! in_loop_pipeline)
kono
parents: 67
diff changeset
1558 {
kono
parents: 67
diff changeset
1559 loop_optimizer_finalize ();
kono
parents: 67
diff changeset
1560 scev_finalize ();
kono
parents: 67
diff changeset
1561 }
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1562
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1563 longest_chain = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1564 total_chain = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1565 nr_walks = 0;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1566 chain_ovfl = false;
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1567 visited = BITMAP_ALLOC (NULL);
111
kono
parents: 67
diff changeset
1568 propagate_necessity (aggressive);
55
77e2b8dfacca update it from 4.4.3 to 4.5.0
ryoma <e075725@ie.u-ryukyu.ac.jp>
parents: 0
diff changeset
1569 BITMAP_FREE (visited);
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1570
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1571 something_changed |= eliminate_unnecessary_stmts ();
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1572 something_changed |= cfg_altered;
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1573
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1574 /* We do not update postdominators, so free them unconditionally. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1575 free_dominance_info (CDI_POST_DOMINATORS);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1576
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1577 /* If we removed paths in the CFG, then we need to update
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1578 dominators as well. I haven't investigated the possibility
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1579 of incrementally updating dominators. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1580 if (cfg_altered)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1581 free_dominance_info (CDI_DOMINATORS);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1582
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1583 statistics_counter_event (cfun, "Statements deleted", stats.removed);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1584 statistics_counter_event (cfun, "PHI nodes deleted", stats.removed_phis);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1585
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1586 /* Debugging dumps. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1587 if (dump_file && (dump_flags & (TDF_STATS|TDF_DETAILS)))
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1588 print_stats ();
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1589
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1590 tree_dce_done (aggressive);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1591
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1592 if (something_changed)
111
kono
parents: 67
diff changeset
1593 {
kono
parents: 67
diff changeset
1594 free_numbers_of_iterations_estimates (cfun);
kono
parents: 67
diff changeset
1595 if (in_loop_pipeline)
kono
parents: 67
diff changeset
1596 scev_reset ();
kono
parents: 67
diff changeset
1597 return TODO_update_ssa | TODO_cleanup_cfg;
kono
parents: 67
diff changeset
1598 }
kono
parents: 67
diff changeset
1599 return 0;
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1600 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1601
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1602 /* Pass entry points. */
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1603 static unsigned int
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1604 tree_ssa_dce (void)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1605 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1606 return perform_tree_ssa_dce (/*aggressive=*/false);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1607 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1608
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1609 static unsigned int
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1610 tree_ssa_cd_dce (void)
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1611 {
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1612 return perform_tree_ssa_dce (/*aggressive=*/optimize >= 2);
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1613 }
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1614
111
kono
parents: 67
diff changeset
1615 namespace {
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1616
111
kono
parents: 67
diff changeset
1617 const pass_data pass_data_dce =
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1618 {
111
kono
parents: 67
diff changeset
1619 GIMPLE_PASS, /* type */
kono
parents: 67
diff changeset
1620 "dce", /* name */
kono
parents: 67
diff changeset
1621 OPTGROUP_NONE, /* optinfo_flags */
kono
parents: 67
diff changeset
1622 TV_TREE_DCE, /* tv_id */
kono
parents: 67
diff changeset
1623 ( PROP_cfg | PROP_ssa ), /* properties_required */
kono
parents: 67
diff changeset
1624 0, /* properties_provided */
kono
parents: 67
diff changeset
1625 0, /* properties_destroyed */
kono
parents: 67
diff changeset
1626 0, /* todo_flags_start */
kono
parents: 67
diff changeset
1627 0, /* todo_flags_finish */
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1628 };
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1629
111
kono
parents: 67
diff changeset
1630 class pass_dce : public gimple_opt_pass
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1631 {
111
kono
parents: 67
diff changeset
1632 public:
kono
parents: 67
diff changeset
1633 pass_dce (gcc::context *ctxt)
kono
parents: 67
diff changeset
1634 : gimple_opt_pass (pass_data_dce, ctxt)
kono
parents: 67
diff changeset
1635 {}
kono
parents: 67
diff changeset
1636
kono
parents: 67
diff changeset
1637 /* opt_pass methods: */
kono
parents: 67
diff changeset
1638 opt_pass * clone () { return new pass_dce (m_ctxt); }
kono
parents: 67
diff changeset
1639 virtual bool gate (function *) { return flag_tree_dce != 0; }
kono
parents: 67
diff changeset
1640 virtual unsigned int execute (function *) { return tree_ssa_dce (); }
kono
parents: 67
diff changeset
1641
kono
parents: 67
diff changeset
1642 }; // class pass_dce
kono
parents: 67
diff changeset
1643
kono
parents: 67
diff changeset
1644 } // anon namespace
kono
parents: 67
diff changeset
1645
kono
parents: 67
diff changeset
1646 gimple_opt_pass *
kono
parents: 67
diff changeset
1647 make_pass_dce (gcc::context *ctxt)
kono
parents: 67
diff changeset
1648 {
kono
parents: 67
diff changeset
1649 return new pass_dce (ctxt);
kono
parents: 67
diff changeset
1650 }
kono
parents: 67
diff changeset
1651
kono
parents: 67
diff changeset
1652 namespace {
kono
parents: 67
diff changeset
1653
kono
parents: 67
diff changeset
1654 const pass_data pass_data_cd_dce =
kono
parents: 67
diff changeset
1655 {
kono
parents: 67
diff changeset
1656 GIMPLE_PASS, /* type */
kono
parents: 67
diff changeset
1657 "cddce", /* name */
kono
parents: 67
diff changeset
1658 OPTGROUP_NONE, /* optinfo_flags */
kono
parents: 67
diff changeset
1659 TV_TREE_CD_DCE, /* tv_id */
kono
parents: 67
diff changeset
1660 ( PROP_cfg | PROP_ssa ), /* properties_required */
kono
parents: 67
diff changeset
1661 0, /* properties_provided */
kono
parents: 67
diff changeset
1662 0, /* properties_destroyed */
kono
parents: 67
diff changeset
1663 0, /* todo_flags_start */
kono
parents: 67
diff changeset
1664 0, /* todo_flags_finish */
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1665 };
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1666
111
kono
parents: 67
diff changeset
1667 class pass_cd_dce : public gimple_opt_pass
0
a06113de4d67 first commit
kent <kent@cr.ie.u-ryukyu.ac.jp>
parents:
diff changeset
1668 {
111
kono
parents: 67
diff changeset
1669 public:
kono
parents: 67
diff changeset
1670 pass_cd_dce (gcc::context *ctxt)
kono
parents: 67
diff changeset
1671 : gimple_opt_pass (pass_data_cd_dce, ctxt)
kono
parents: 67
diff changeset
1672 {}
kono
parents: 67
diff changeset
1673
kono
parents: 67
diff changeset
1674 /* opt_pass methods: */
kono
parents: 67
diff changeset
1675 opt_pass * clone () { return new pass_cd_dce (m_ctxt); }
kono
parents: 67
diff changeset
1676 virtual bool gate (function *) { return flag_tree_dce != 0; }
kono
parents: 67
diff changeset
1677 virtual unsigned int execute (function *) { return tree_ssa_cd_dce (); }
kono
parents: 67
diff changeset
1678
kono
parents: 67
diff changeset
1679 }; // class pass_cd_dce
kono
parents: 67
diff changeset
1680
kono
parents: 67
diff changeset
1681 } // anon namespace
kono
parents: 67
diff changeset
1682
kono
parents: 67
diff changeset
1683 gimple_opt_pass *
kono
parents: 67
diff changeset
1684 make_pass_cd_dce (gcc::context *ctxt)
kono
parents: 67
diff changeset
1685 {
kono
parents: 67
diff changeset
1686 return new pass_cd_dce (ctxt);
kono
parents: 67
diff changeset
1687 }
131
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1688
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1689
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1690 /* A cheap DCE interface. WORKLIST is a list of possibly dead stmts and
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1691 is consumed by this function. The function has linear complexity in
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1692 the number of dead stmts with a constant factor like the average SSA
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1693 use operands number. */
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1694
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1695 void
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1696 simple_dce_from_worklist (bitmap worklist)
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1697 {
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1698 while (! bitmap_empty_p (worklist))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1699 {
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1700 /* Pop item. */
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1701 unsigned i = bitmap_first_set_bit (worklist);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1702 bitmap_clear_bit (worklist, i);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1703
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1704 tree def = ssa_name (i);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1705 /* Removed by somebody else or still in use. */
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1706 if (! def || ! has_zero_uses (def))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1707 continue;
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1708
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1709 gimple *t = SSA_NAME_DEF_STMT (def);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1710 if (gimple_has_side_effects (t))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1711 continue;
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1712
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1713 /* Add uses to the worklist. */
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1714 ssa_op_iter iter;
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1715 use_operand_p use_p;
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1716 FOR_EACH_PHI_OR_STMT_USE (use_p, t, iter, SSA_OP_USE)
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1717 {
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1718 tree use = USE_FROM_PTR (use_p);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1719 if (TREE_CODE (use) == SSA_NAME
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1720 && ! SSA_NAME_IS_DEFAULT_DEF (use))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1721 bitmap_set_bit (worklist, SSA_NAME_VERSION (use));
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1722 }
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1723
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1724 /* Remove stmt. */
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1725 if (dump_file && (dump_flags & TDF_DETAILS))
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1726 {
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1727 fprintf (dump_file, "Removing dead stmt:");
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1728 print_gimple_stmt (dump_file, t, 0);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1729 }
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1730 gimple_stmt_iterator gsi = gsi_for_stmt (t);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1731 if (gimple_code (t) == GIMPLE_PHI)
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1732 remove_phi_node (&gsi, true);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1733 else
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1734 {
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1735 gsi_remove (&gsi, true);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1736 release_defs (t);
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1737 }
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1738 }
84e7813d76e9 gcc-8.2
mir3636
parents: 111
diff changeset
1739 }