1*e4b17023SJohn Marino /* Web construction code for GNU compiler.
2*e4b17023SJohn Marino Contributed by Jan Hubicka.
3*e4b17023SJohn Marino Copyright (C) 2001, 2002, 2004, 2006, 2007, 2008, 2010
4*e4b17023SJohn Marino Free Software Foundation, Inc.
5*e4b17023SJohn Marino
6*e4b17023SJohn Marino This file is part of GCC.
7*e4b17023SJohn Marino
8*e4b17023SJohn Marino GCC is free software; you can redistribute it and/or modify it under
9*e4b17023SJohn Marino the terms of the GNU General Public License as published by the Free
10*e4b17023SJohn Marino Software Foundation; either version 3, or (at your option) any later
11*e4b17023SJohn Marino version.
12*e4b17023SJohn Marino
13*e4b17023SJohn Marino GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14*e4b17023SJohn Marino WARRANTY; without even the implied warranty of MERCHANTABILITY or
15*e4b17023SJohn Marino FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16*e4b17023SJohn Marino for more details.
17*e4b17023SJohn Marino
18*e4b17023SJohn Marino You should have received a copy of the GNU General Public License
19*e4b17023SJohn Marino along with GCC; see the file COPYING3. If not see
20*e4b17023SJohn Marino <http://www.gnu.org/licenses/>. */
21*e4b17023SJohn Marino
22*e4b17023SJohn Marino /* Simple optimization pass that splits independent uses of each pseudo,
23*e4b17023SJohn Marino increasing effectiveness of other optimizations. The optimization can
24*e4b17023SJohn Marino serve as an example of use for the dataflow module.
25*e4b17023SJohn Marino
26*e4b17023SJohn Marino We don't split registers with REG_USERVAR set unless -fmessy-debugging
27*e4b17023SJohn Marino is specified, because debugging information about such split variables
28*e4b17023SJohn Marino is almost unusable.
29*e4b17023SJohn Marino
30*e4b17023SJohn Marino TODO
31*e4b17023SJohn Marino - We may use profile information and ignore infrequent use for the
32*e4b17023SJohn Marino purpose of web unifying, inserting the compensation code later to
33*e4b17023SJohn Marino implement full induction variable expansion for loops (currently
34*e4b17023SJohn Marino we expand only if the induction variable is dead afterward, which
35*e4b17023SJohn Marino is often the case). */
36*e4b17023SJohn Marino
37*e4b17023SJohn Marino #include "config.h"
38*e4b17023SJohn Marino #include "system.h"
39*e4b17023SJohn Marino #include "coretypes.h"
40*e4b17023SJohn Marino #include "tm.h"
41*e4b17023SJohn Marino #include "diagnostic-core.h"
42*e4b17023SJohn Marino
43*e4b17023SJohn Marino #include "rtl.h"
44*e4b17023SJohn Marino #include "hard-reg-set.h"
45*e4b17023SJohn Marino #include "flags.h"
46*e4b17023SJohn Marino #include "obstack.h"
47*e4b17023SJohn Marino #include "basic-block.h"
48*e4b17023SJohn Marino #include "output.h"
49*e4b17023SJohn Marino #include "df.h"
50*e4b17023SJohn Marino #include "function.h"
51*e4b17023SJohn Marino #include "insn-config.h"
52*e4b17023SJohn Marino #include "recog.h"
53*e4b17023SJohn Marino #include "timevar.h"
54*e4b17023SJohn Marino #include "tree-pass.h"
55*e4b17023SJohn Marino
56*e4b17023SJohn Marino
57*e4b17023SJohn Marino /* Find the root of unionfind tree (the representative of set). */
58*e4b17023SJohn Marino
59*e4b17023SJohn Marino struct web_entry *
unionfind_root(struct web_entry * element)60*e4b17023SJohn Marino unionfind_root (struct web_entry *element)
61*e4b17023SJohn Marino {
62*e4b17023SJohn Marino struct web_entry *element1 = element, *element2;
63*e4b17023SJohn Marino
64*e4b17023SJohn Marino while (element->pred)
65*e4b17023SJohn Marino element = element->pred;
66*e4b17023SJohn Marino while (element1->pred)
67*e4b17023SJohn Marino {
68*e4b17023SJohn Marino element2 = element1->pred;
69*e4b17023SJohn Marino element1->pred = element;
70*e4b17023SJohn Marino element1 = element2;
71*e4b17023SJohn Marino }
72*e4b17023SJohn Marino return element;
73*e4b17023SJohn Marino }
74*e4b17023SJohn Marino
75*e4b17023SJohn Marino /* Union sets.
76*e4b17023SJohn Marino Return true if FIRST and SECOND points to the same web entry structure and
77*e4b17023SJohn Marino nothing is done. Otherwise, return false. */
78*e4b17023SJohn Marino
79*e4b17023SJohn Marino bool
unionfind_union(struct web_entry * first,struct web_entry * second)80*e4b17023SJohn Marino unionfind_union (struct web_entry *first, struct web_entry *second)
81*e4b17023SJohn Marino {
82*e4b17023SJohn Marino first = unionfind_root (first);
83*e4b17023SJohn Marino second = unionfind_root (second);
84*e4b17023SJohn Marino if (first == second)
85*e4b17023SJohn Marino return true;
86*e4b17023SJohn Marino second->pred = first;
87*e4b17023SJohn Marino return false;
88*e4b17023SJohn Marino }
89*e4b17023SJohn Marino
90*e4b17023SJohn Marino /* For INSN, union all defs and uses that are linked by match_dup.
91*e4b17023SJohn Marino FUN is the function that does the union. */
92*e4b17023SJohn Marino
93*e4b17023SJohn Marino static void
union_match_dups(rtx insn,struct web_entry * def_entry,struct web_entry * use_entry,bool (* fun)(struct web_entry *,struct web_entry *))94*e4b17023SJohn Marino union_match_dups (rtx insn, struct web_entry *def_entry,
95*e4b17023SJohn Marino struct web_entry *use_entry,
96*e4b17023SJohn Marino bool (*fun) (struct web_entry *, struct web_entry *))
97*e4b17023SJohn Marino {
98*e4b17023SJohn Marino struct df_insn_info *insn_info = DF_INSN_INFO_GET (insn);
99*e4b17023SJohn Marino df_ref *use_link = DF_INSN_INFO_USES (insn_info);
100*e4b17023SJohn Marino df_ref *def_link = DF_INSN_INFO_DEFS (insn_info);
101*e4b17023SJohn Marino int i;
102*e4b17023SJohn Marino
103*e4b17023SJohn Marino extract_insn (insn);
104*e4b17023SJohn Marino
105*e4b17023SJohn Marino for (i = 0; i < recog_data.n_dups; i++)
106*e4b17023SJohn Marino {
107*e4b17023SJohn Marino int op = recog_data.dup_num[i];
108*e4b17023SJohn Marino enum op_type type = recog_data.operand_type[op];
109*e4b17023SJohn Marino df_ref *ref, *dupref;
110*e4b17023SJohn Marino struct web_entry *entry;
111*e4b17023SJohn Marino
112*e4b17023SJohn Marino for (dupref = use_link; *dupref; dupref++)
113*e4b17023SJohn Marino if (DF_REF_LOC (*dupref) == recog_data.dup_loc[i])
114*e4b17023SJohn Marino break;
115*e4b17023SJohn Marino
116*e4b17023SJohn Marino if (*dupref == NULL
117*e4b17023SJohn Marino || DF_REF_REGNO (*dupref) < FIRST_PSEUDO_REGISTER)
118*e4b17023SJohn Marino continue;
119*e4b17023SJohn Marino
120*e4b17023SJohn Marino ref = type == OP_IN ? use_link : def_link;
121*e4b17023SJohn Marino entry = type == OP_IN ? use_entry : def_entry;
122*e4b17023SJohn Marino for (; *ref; ref++)
123*e4b17023SJohn Marino if (DF_REF_LOC (*ref) == recog_data.operand_loc[op])
124*e4b17023SJohn Marino break;
125*e4b17023SJohn Marino
126*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (*dupref), entry + DF_REF_ID (*ref));
127*e4b17023SJohn Marino }
128*e4b17023SJohn Marino }
129*e4b17023SJohn Marino
130*e4b17023SJohn Marino /* For each use, all possible defs reaching it must come in the same
131*e4b17023SJohn Marino register, union them.
132*e4b17023SJohn Marino FUN is the function that does the union.
133*e4b17023SJohn Marino
134*e4b17023SJohn Marino In USED, we keep the DF_REF_ID of the first uninitialized uses of a
135*e4b17023SJohn Marino register, so that all uninitialized uses of the register can be
136*e4b17023SJohn Marino combined into a single web. We actually offset it by 2, because
137*e4b17023SJohn Marino the values 0 and 1 are reserved for use by entry_register. */
138*e4b17023SJohn Marino
139*e4b17023SJohn Marino void
union_defs(df_ref use,struct web_entry * def_entry,unsigned int * used,struct web_entry * use_entry,bool (* fun)(struct web_entry *,struct web_entry *))140*e4b17023SJohn Marino union_defs (df_ref use, struct web_entry *def_entry,
141*e4b17023SJohn Marino unsigned int *used, struct web_entry *use_entry,
142*e4b17023SJohn Marino bool (*fun) (struct web_entry *, struct web_entry *))
143*e4b17023SJohn Marino {
144*e4b17023SJohn Marino struct df_insn_info *insn_info = DF_REF_INSN_INFO (use);
145*e4b17023SJohn Marino struct df_link *link = DF_REF_CHAIN (use);
146*e4b17023SJohn Marino df_ref *eq_use_link;
147*e4b17023SJohn Marino df_ref *def_link;
148*e4b17023SJohn Marino rtx set;
149*e4b17023SJohn Marino
150*e4b17023SJohn Marino if (insn_info)
151*e4b17023SJohn Marino {
152*e4b17023SJohn Marino rtx insn = insn_info->insn;
153*e4b17023SJohn Marino eq_use_link = DF_INSN_INFO_EQ_USES (insn_info);
154*e4b17023SJohn Marino def_link = DF_INSN_INFO_DEFS (insn_info);
155*e4b17023SJohn Marino set = single_set (insn);
156*e4b17023SJohn Marino }
157*e4b17023SJohn Marino else
158*e4b17023SJohn Marino {
159*e4b17023SJohn Marino /* An artificial use. It links up with nothing. */
160*e4b17023SJohn Marino eq_use_link = NULL;
161*e4b17023SJohn Marino def_link = NULL;
162*e4b17023SJohn Marino set = NULL;
163*e4b17023SJohn Marino }
164*e4b17023SJohn Marino
165*e4b17023SJohn Marino /* Union all occurrences of the same register in reg notes. */
166*e4b17023SJohn Marino
167*e4b17023SJohn Marino if (eq_use_link)
168*e4b17023SJohn Marino while (*eq_use_link)
169*e4b17023SJohn Marino {
170*e4b17023SJohn Marino if (use != *eq_use_link
171*e4b17023SJohn Marino && DF_REF_REAL_REG (use) == DF_REF_REAL_REG (*eq_use_link))
172*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (use),
173*e4b17023SJohn Marino use_entry + DF_REF_ID (*eq_use_link));
174*e4b17023SJohn Marino eq_use_link++;
175*e4b17023SJohn Marino }
176*e4b17023SJohn Marino
177*e4b17023SJohn Marino /* Recognize trivial noop moves and attempt to keep them as noop. */
178*e4b17023SJohn Marino
179*e4b17023SJohn Marino if (set
180*e4b17023SJohn Marino && SET_SRC (set) == DF_REF_REG (use)
181*e4b17023SJohn Marino && SET_SRC (set) == SET_DEST (set))
182*e4b17023SJohn Marino {
183*e4b17023SJohn Marino if (def_link)
184*e4b17023SJohn Marino while (*def_link)
185*e4b17023SJohn Marino {
186*e4b17023SJohn Marino if (DF_REF_REAL_REG (use) == DF_REF_REAL_REG (*def_link))
187*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (use),
188*e4b17023SJohn Marino def_entry + DF_REF_ID (*def_link));
189*e4b17023SJohn Marino def_link++;
190*e4b17023SJohn Marino }
191*e4b17023SJohn Marino }
192*e4b17023SJohn Marino
193*e4b17023SJohn Marino /* UD chains of uninitialized REGs are empty. Keeping all uses of
194*e4b17023SJohn Marino the same uninitialized REG in a single web is not necessary for
195*e4b17023SJohn Marino correctness, since the uses are undefined, but it's wasteful to
196*e4b17023SJohn Marino allocate one register or slot for each reference. Furthermore,
197*e4b17023SJohn Marino creating new pseudos for uninitialized references in debug insns
198*e4b17023SJohn Marino (see PR 42631) causes -fcompare-debug failures. We record the
199*e4b17023SJohn Marino number of the first uninitialized reference we found, and merge
200*e4b17023SJohn Marino with it any other uninitialized references to the same
201*e4b17023SJohn Marino register. */
202*e4b17023SJohn Marino if (!link)
203*e4b17023SJohn Marino {
204*e4b17023SJohn Marino int regno = REGNO (DF_REF_REAL_REG (use));
205*e4b17023SJohn Marino if (used[regno])
206*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (use), use_entry + used[regno] - 2);
207*e4b17023SJohn Marino else
208*e4b17023SJohn Marino used[regno] = DF_REF_ID (use) + 2;
209*e4b17023SJohn Marino }
210*e4b17023SJohn Marino
211*e4b17023SJohn Marino while (link)
212*e4b17023SJohn Marino {
213*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (use),
214*e4b17023SJohn Marino def_entry + DF_REF_ID (link->ref));
215*e4b17023SJohn Marino link = link->next;
216*e4b17023SJohn Marino }
217*e4b17023SJohn Marino
218*e4b17023SJohn Marino /* A READ_WRITE use requires the corresponding def to be in the same
219*e4b17023SJohn Marino register. Find it and union. */
220*e4b17023SJohn Marino if (DF_REF_FLAGS (use) & DF_REF_READ_WRITE)
221*e4b17023SJohn Marino {
222*e4b17023SJohn Marino df_ref *link;
223*e4b17023SJohn Marino
224*e4b17023SJohn Marino if (insn_info)
225*e4b17023SJohn Marino link = DF_INSN_INFO_DEFS (insn_info);
226*e4b17023SJohn Marino else
227*e4b17023SJohn Marino link = NULL;
228*e4b17023SJohn Marino
229*e4b17023SJohn Marino if (link)
230*e4b17023SJohn Marino while (*link)
231*e4b17023SJohn Marino {
232*e4b17023SJohn Marino if (DF_REF_REAL_REG (*link) == DF_REF_REAL_REG (use))
233*e4b17023SJohn Marino (*fun) (use_entry + DF_REF_ID (use),
234*e4b17023SJohn Marino def_entry + DF_REF_ID (*link));
235*e4b17023SJohn Marino link++;
236*e4b17023SJohn Marino }
237*e4b17023SJohn Marino }
238*e4b17023SJohn Marino }
239*e4b17023SJohn Marino
240*e4b17023SJohn Marino /* Find the corresponding register for the given entry. */
241*e4b17023SJohn Marino
242*e4b17023SJohn Marino static rtx
entry_register(struct web_entry * entry,df_ref ref,unsigned int * used)243*e4b17023SJohn Marino entry_register (struct web_entry *entry, df_ref ref, unsigned int *used)
244*e4b17023SJohn Marino {
245*e4b17023SJohn Marino struct web_entry *root;
246*e4b17023SJohn Marino rtx reg, newreg;
247*e4b17023SJohn Marino
248*e4b17023SJohn Marino /* Find the corresponding web and see if it has been visited. */
249*e4b17023SJohn Marino root = unionfind_root (entry);
250*e4b17023SJohn Marino if (root->reg)
251*e4b17023SJohn Marino return root->reg;
252*e4b17023SJohn Marino
253*e4b17023SJohn Marino /* We are seeing this web for the first time, do the assignment. */
254*e4b17023SJohn Marino reg = DF_REF_REAL_REG (ref);
255*e4b17023SJohn Marino
256*e4b17023SJohn Marino /* In case the original register is already assigned, generate new
257*e4b17023SJohn Marino one. Since we use USED to merge uninitialized refs into a single
258*e4b17023SJohn Marino web, we might found an element to be nonzero without our having
259*e4b17023SJohn Marino used it. Test for 1, because union_defs saves it for our use,
260*e4b17023SJohn Marino and there won't be any use for the other values when we get to
261*e4b17023SJohn Marino this point. */
262*e4b17023SJohn Marino if (used[REGNO (reg)] != 1)
263*e4b17023SJohn Marino newreg = reg, used[REGNO (reg)] = 1;
264*e4b17023SJohn Marino else
265*e4b17023SJohn Marino {
266*e4b17023SJohn Marino newreg = gen_reg_rtx (GET_MODE (reg));
267*e4b17023SJohn Marino REG_USERVAR_P (newreg) = REG_USERVAR_P (reg);
268*e4b17023SJohn Marino REG_POINTER (newreg) = REG_POINTER (reg);
269*e4b17023SJohn Marino REG_ATTRS (newreg) = REG_ATTRS (reg);
270*e4b17023SJohn Marino if (dump_file)
271*e4b17023SJohn Marino fprintf (dump_file, "Web oldreg=%i newreg=%i\n", REGNO (reg),
272*e4b17023SJohn Marino REGNO (newreg));
273*e4b17023SJohn Marino }
274*e4b17023SJohn Marino
275*e4b17023SJohn Marino root->reg = newreg;
276*e4b17023SJohn Marino return newreg;
277*e4b17023SJohn Marino }
278*e4b17023SJohn Marino
279*e4b17023SJohn Marino /* Replace the reference by REG. */
280*e4b17023SJohn Marino
281*e4b17023SJohn Marino static void
replace_ref(df_ref ref,rtx reg)282*e4b17023SJohn Marino replace_ref (df_ref ref, rtx reg)
283*e4b17023SJohn Marino {
284*e4b17023SJohn Marino rtx oldreg = DF_REF_REAL_REG (ref);
285*e4b17023SJohn Marino rtx *loc = DF_REF_REAL_LOC (ref);
286*e4b17023SJohn Marino unsigned int uid = DF_REF_INSN_UID (ref);
287*e4b17023SJohn Marino
288*e4b17023SJohn Marino if (oldreg == reg)
289*e4b17023SJohn Marino return;
290*e4b17023SJohn Marino if (dump_file)
291*e4b17023SJohn Marino fprintf (dump_file, "Updating insn %i (%i->%i)\n",
292*e4b17023SJohn Marino uid, REGNO (oldreg), REGNO (reg));
293*e4b17023SJohn Marino *loc = reg;
294*e4b17023SJohn Marino df_insn_rescan (DF_REF_INSN (ref));
295*e4b17023SJohn Marino }
296*e4b17023SJohn Marino
297*e4b17023SJohn Marino
298*e4b17023SJohn Marino static bool
gate_handle_web(void)299*e4b17023SJohn Marino gate_handle_web (void)
300*e4b17023SJohn Marino {
301*e4b17023SJohn Marino return (optimize > 0 && flag_web);
302*e4b17023SJohn Marino }
303*e4b17023SJohn Marino
304*e4b17023SJohn Marino /* Main entry point. */
305*e4b17023SJohn Marino
306*e4b17023SJohn Marino static unsigned int
web_main(void)307*e4b17023SJohn Marino web_main (void)
308*e4b17023SJohn Marino {
309*e4b17023SJohn Marino struct web_entry *def_entry;
310*e4b17023SJohn Marino struct web_entry *use_entry;
311*e4b17023SJohn Marino unsigned int max = max_reg_num ();
312*e4b17023SJohn Marino unsigned int *used;
313*e4b17023SJohn Marino basic_block bb;
314*e4b17023SJohn Marino unsigned int uses_num = 0;
315*e4b17023SJohn Marino rtx insn;
316*e4b17023SJohn Marino
317*e4b17023SJohn Marino df_set_flags (DF_NO_HARD_REGS + DF_EQ_NOTES);
318*e4b17023SJohn Marino df_chain_add_problem (DF_UD_CHAIN);
319*e4b17023SJohn Marino df_analyze ();
320*e4b17023SJohn Marino df_set_flags (DF_DEFER_INSN_RESCAN);
321*e4b17023SJohn Marino
322*e4b17023SJohn Marino /* Assign ids to the uses. */
323*e4b17023SJohn Marino FOR_ALL_BB (bb)
324*e4b17023SJohn Marino FOR_BB_INSNS (bb, insn)
325*e4b17023SJohn Marino {
326*e4b17023SJohn Marino unsigned int uid = INSN_UID (insn);
327*e4b17023SJohn Marino if (NONDEBUG_INSN_P (insn))
328*e4b17023SJohn Marino {
329*e4b17023SJohn Marino df_ref *use_rec;
330*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_USES (uid); *use_rec; use_rec++)
331*e4b17023SJohn Marino {
332*e4b17023SJohn Marino df_ref use = *use_rec;
333*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
334*e4b17023SJohn Marino DF_REF_ID (use) = uses_num++;
335*e4b17023SJohn Marino }
336*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_EQ_USES (uid); *use_rec; use_rec++)
337*e4b17023SJohn Marino {
338*e4b17023SJohn Marino df_ref use = *use_rec;
339*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
340*e4b17023SJohn Marino DF_REF_ID (use) = uses_num++;
341*e4b17023SJohn Marino }
342*e4b17023SJohn Marino }
343*e4b17023SJohn Marino }
344*e4b17023SJohn Marino
345*e4b17023SJohn Marino /* Record the number of uses and defs at the beginning of the optimization. */
346*e4b17023SJohn Marino def_entry = XCNEWVEC (struct web_entry, DF_DEFS_TABLE_SIZE());
347*e4b17023SJohn Marino used = XCNEWVEC (unsigned, max);
348*e4b17023SJohn Marino use_entry = XCNEWVEC (struct web_entry, uses_num);
349*e4b17023SJohn Marino
350*e4b17023SJohn Marino /* Produce the web. */
351*e4b17023SJohn Marino FOR_ALL_BB (bb)
352*e4b17023SJohn Marino FOR_BB_INSNS (bb, insn)
353*e4b17023SJohn Marino {
354*e4b17023SJohn Marino unsigned int uid = INSN_UID (insn);
355*e4b17023SJohn Marino if (NONDEBUG_INSN_P (insn))
356*e4b17023SJohn Marino {
357*e4b17023SJohn Marino df_ref *use_rec;
358*e4b17023SJohn Marino union_match_dups (insn, def_entry, use_entry, unionfind_union);
359*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_USES (uid); *use_rec; use_rec++)
360*e4b17023SJohn Marino {
361*e4b17023SJohn Marino df_ref use = *use_rec;
362*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
363*e4b17023SJohn Marino union_defs (use, def_entry, used, use_entry, unionfind_union);
364*e4b17023SJohn Marino }
365*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_EQ_USES (uid); *use_rec; use_rec++)
366*e4b17023SJohn Marino {
367*e4b17023SJohn Marino df_ref use = *use_rec;
368*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
369*e4b17023SJohn Marino union_defs (use, def_entry, used, use_entry, unionfind_union);
370*e4b17023SJohn Marino }
371*e4b17023SJohn Marino }
372*e4b17023SJohn Marino }
373*e4b17023SJohn Marino
374*e4b17023SJohn Marino /* Update the instruction stream, allocating new registers for split pseudos
375*e4b17023SJohn Marino in progress. */
376*e4b17023SJohn Marino FOR_ALL_BB (bb)
377*e4b17023SJohn Marino FOR_BB_INSNS (bb, insn)
378*e4b17023SJohn Marino {
379*e4b17023SJohn Marino unsigned int uid = INSN_UID (insn);
380*e4b17023SJohn Marino
381*e4b17023SJohn Marino if (NONDEBUG_INSN_P (insn)
382*e4b17023SJohn Marino /* Ignore naked clobber. For example, reg 134 in the second insn
383*e4b17023SJohn Marino of the following sequence will not be replaced.
384*e4b17023SJohn Marino
385*e4b17023SJohn Marino (insn (clobber (reg:SI 134)))
386*e4b17023SJohn Marino
387*e4b17023SJohn Marino (insn (set (reg:SI 0 r0) (reg:SI 134)))
388*e4b17023SJohn Marino
389*e4b17023SJohn Marino Thus the later passes can optimize them away. */
390*e4b17023SJohn Marino && GET_CODE (PATTERN (insn)) != CLOBBER)
391*e4b17023SJohn Marino {
392*e4b17023SJohn Marino df_ref *use_rec;
393*e4b17023SJohn Marino df_ref *def_rec;
394*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_USES (uid); *use_rec; use_rec++)
395*e4b17023SJohn Marino {
396*e4b17023SJohn Marino df_ref use = *use_rec;
397*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
398*e4b17023SJohn Marino replace_ref (use, entry_register (use_entry + DF_REF_ID (use), use, used));
399*e4b17023SJohn Marino }
400*e4b17023SJohn Marino for (use_rec = DF_INSN_UID_EQ_USES (uid); *use_rec; use_rec++)
401*e4b17023SJohn Marino {
402*e4b17023SJohn Marino df_ref use = *use_rec;
403*e4b17023SJohn Marino if (DF_REF_REGNO (use) >= FIRST_PSEUDO_REGISTER)
404*e4b17023SJohn Marino replace_ref (use, entry_register (use_entry + DF_REF_ID (use), use, used));
405*e4b17023SJohn Marino }
406*e4b17023SJohn Marino for (def_rec = DF_INSN_UID_DEFS (uid); *def_rec; def_rec++)
407*e4b17023SJohn Marino {
408*e4b17023SJohn Marino df_ref def = *def_rec;
409*e4b17023SJohn Marino if (DF_REF_REGNO (def) >= FIRST_PSEUDO_REGISTER)
410*e4b17023SJohn Marino replace_ref (def, entry_register (def_entry + DF_REF_ID (def), def, used));
411*e4b17023SJohn Marino }
412*e4b17023SJohn Marino }
413*e4b17023SJohn Marino }
414*e4b17023SJohn Marino
415*e4b17023SJohn Marino free (def_entry);
416*e4b17023SJohn Marino free (use_entry);
417*e4b17023SJohn Marino free (used);
418*e4b17023SJohn Marino return 0;
419*e4b17023SJohn Marino }
420*e4b17023SJohn Marino
421*e4b17023SJohn Marino struct rtl_opt_pass pass_web =
422*e4b17023SJohn Marino {
423*e4b17023SJohn Marino {
424*e4b17023SJohn Marino RTL_PASS,
425*e4b17023SJohn Marino "web", /* name */
426*e4b17023SJohn Marino gate_handle_web, /* gate */
427*e4b17023SJohn Marino web_main, /* execute */
428*e4b17023SJohn Marino NULL, /* sub */
429*e4b17023SJohn Marino NULL, /* next */
430*e4b17023SJohn Marino 0, /* static_pass_number */
431*e4b17023SJohn Marino TV_WEB, /* tv_id */
432*e4b17023SJohn Marino 0, /* properties_required */
433*e4b17023SJohn Marino 0, /* properties_provided */
434*e4b17023SJohn Marino 0, /* properties_destroyed */
435*e4b17023SJohn Marino 0, /* todo_flags_start */
436*e4b17023SJohn Marino TODO_df_finish | TODO_verify_rtl_sharing /* todo_flags_finish */
437*e4b17023SJohn Marino }
438*e4b17023SJohn Marino };
439