1*e4b17023SJohn Marino /* Definitions for computing resource usage of specific insns.
2*e4b17023SJohn Marino Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008,
3*e4b17023SJohn Marino 2009, 2010 Free Software Foundation, Inc.
4*e4b17023SJohn Marino
5*e4b17023SJohn Marino This file is part of GCC.
6*e4b17023SJohn Marino
7*e4b17023SJohn Marino GCC is free software; you can redistribute it and/or modify it under
8*e4b17023SJohn Marino the terms of the GNU General Public License as published by the Free
9*e4b17023SJohn Marino Software Foundation; either version 3, or (at your option) any later
10*e4b17023SJohn Marino version.
11*e4b17023SJohn Marino
12*e4b17023SJohn Marino GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13*e4b17023SJohn Marino WARRANTY; without even the implied warranty of MERCHANTABILITY or
14*e4b17023SJohn Marino FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15*e4b17023SJohn Marino for more details.
16*e4b17023SJohn Marino
17*e4b17023SJohn Marino You should have received a copy of the GNU General Public License
18*e4b17023SJohn Marino along with GCC; see the file COPYING3. If not see
19*e4b17023SJohn Marino <http://www.gnu.org/licenses/>. */
20*e4b17023SJohn Marino
21*e4b17023SJohn Marino #include "config.h"
22*e4b17023SJohn Marino #include "system.h"
23*e4b17023SJohn Marino #include "coretypes.h"
24*e4b17023SJohn Marino #include "tm.h"
25*e4b17023SJohn Marino #include "diagnostic-core.h"
26*e4b17023SJohn Marino #include "rtl.h"
27*e4b17023SJohn Marino #include "tm_p.h"
28*e4b17023SJohn Marino #include "hard-reg-set.h"
29*e4b17023SJohn Marino #include "function.h"
30*e4b17023SJohn Marino #include "regs.h"
31*e4b17023SJohn Marino #include "flags.h"
32*e4b17023SJohn Marino #include "output.h"
33*e4b17023SJohn Marino #include "resource.h"
34*e4b17023SJohn Marino #include "except.h"
35*e4b17023SJohn Marino #include "insn-attr.h"
36*e4b17023SJohn Marino #include "params.h"
37*e4b17023SJohn Marino #include "df.h"
38*e4b17023SJohn Marino
39*e4b17023SJohn Marino /* This structure is used to record liveness information at the targets or
40*e4b17023SJohn Marino fallthrough insns of branches. We will most likely need the information
41*e4b17023SJohn Marino at targets again, so save them in a hash table rather than recomputing them
42*e4b17023SJohn Marino each time. */
43*e4b17023SJohn Marino
44*e4b17023SJohn Marino struct target_info
45*e4b17023SJohn Marino {
46*e4b17023SJohn Marino int uid; /* INSN_UID of target. */
47*e4b17023SJohn Marino struct target_info *next; /* Next info for same hash bucket. */
48*e4b17023SJohn Marino HARD_REG_SET live_regs; /* Registers live at target. */
49*e4b17023SJohn Marino int block; /* Basic block number containing target. */
50*e4b17023SJohn Marino int bb_tick; /* Generation count of basic block info. */
51*e4b17023SJohn Marino };
52*e4b17023SJohn Marino
53*e4b17023SJohn Marino #define TARGET_HASH_PRIME 257
54*e4b17023SJohn Marino
55*e4b17023SJohn Marino /* Indicates what resources are required at the beginning of the epilogue. */
56*e4b17023SJohn Marino static struct resources start_of_epilogue_needs;
57*e4b17023SJohn Marino
58*e4b17023SJohn Marino /* Indicates what resources are required at function end. */
59*e4b17023SJohn Marino static struct resources end_of_function_needs;
60*e4b17023SJohn Marino
61*e4b17023SJohn Marino /* Define the hash table itself. */
62*e4b17023SJohn Marino static struct target_info **target_hash_table = NULL;
63*e4b17023SJohn Marino
64*e4b17023SJohn Marino /* For each basic block, we maintain a generation number of its basic
65*e4b17023SJohn Marino block info, which is updated each time we move an insn from the
66*e4b17023SJohn Marino target of a jump. This is the generation number indexed by block
67*e4b17023SJohn Marino number. */
68*e4b17023SJohn Marino
69*e4b17023SJohn Marino static int *bb_ticks;
70*e4b17023SJohn Marino
71*e4b17023SJohn Marino /* Marks registers possibly live at the current place being scanned by
72*e4b17023SJohn Marino mark_target_live_regs. Also used by update_live_status. */
73*e4b17023SJohn Marino
74*e4b17023SJohn Marino static HARD_REG_SET current_live_regs;
75*e4b17023SJohn Marino
76*e4b17023SJohn Marino /* Marks registers for which we have seen a REG_DEAD note but no assignment.
77*e4b17023SJohn Marino Also only used by the next two functions. */
78*e4b17023SJohn Marino
79*e4b17023SJohn Marino static HARD_REG_SET pending_dead_regs;
80*e4b17023SJohn Marino
81*e4b17023SJohn Marino static void update_live_status (rtx, const_rtx, void *);
82*e4b17023SJohn Marino static int find_basic_block (rtx, int);
83*e4b17023SJohn Marino static rtx next_insn_no_annul (rtx);
84*e4b17023SJohn Marino static rtx find_dead_or_set_registers (rtx, struct resources*,
85*e4b17023SJohn Marino rtx*, int, struct resources,
86*e4b17023SJohn Marino struct resources);
87*e4b17023SJohn Marino
88*e4b17023SJohn Marino /* Utility function called from mark_target_live_regs via note_stores.
89*e4b17023SJohn Marino It deadens any CLOBBERed registers and livens any SET registers. */
90*e4b17023SJohn Marino
91*e4b17023SJohn Marino static void
update_live_status(rtx dest,const_rtx x,void * data ATTRIBUTE_UNUSED)92*e4b17023SJohn Marino update_live_status (rtx dest, const_rtx x, void *data ATTRIBUTE_UNUSED)
93*e4b17023SJohn Marino {
94*e4b17023SJohn Marino int first_regno, last_regno;
95*e4b17023SJohn Marino int i;
96*e4b17023SJohn Marino
97*e4b17023SJohn Marino if (!REG_P (dest)
98*e4b17023SJohn Marino && (GET_CODE (dest) != SUBREG || !REG_P (SUBREG_REG (dest))))
99*e4b17023SJohn Marino return;
100*e4b17023SJohn Marino
101*e4b17023SJohn Marino if (GET_CODE (dest) == SUBREG)
102*e4b17023SJohn Marino {
103*e4b17023SJohn Marino first_regno = subreg_regno (dest);
104*e4b17023SJohn Marino last_regno = first_regno + subreg_nregs (dest);
105*e4b17023SJohn Marino
106*e4b17023SJohn Marino }
107*e4b17023SJohn Marino else
108*e4b17023SJohn Marino {
109*e4b17023SJohn Marino first_regno = REGNO (dest);
110*e4b17023SJohn Marino last_regno = END_HARD_REGNO (dest);
111*e4b17023SJohn Marino }
112*e4b17023SJohn Marino
113*e4b17023SJohn Marino if (GET_CODE (x) == CLOBBER)
114*e4b17023SJohn Marino for (i = first_regno; i < last_regno; i++)
115*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (current_live_regs, i);
116*e4b17023SJohn Marino else
117*e4b17023SJohn Marino for (i = first_regno; i < last_regno; i++)
118*e4b17023SJohn Marino {
119*e4b17023SJohn Marino SET_HARD_REG_BIT (current_live_regs, i);
120*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (pending_dead_regs, i);
121*e4b17023SJohn Marino }
122*e4b17023SJohn Marino }
123*e4b17023SJohn Marino
124*e4b17023SJohn Marino /* Find the number of the basic block with correct live register
125*e4b17023SJohn Marino information that starts closest to INSN. Return -1 if we couldn't
126*e4b17023SJohn Marino find such a basic block or the beginning is more than
127*e4b17023SJohn Marino SEARCH_LIMIT instructions before INSN. Use SEARCH_LIMIT = -1 for
128*e4b17023SJohn Marino an unlimited search.
129*e4b17023SJohn Marino
130*e4b17023SJohn Marino The delay slot filling code destroys the control-flow graph so,
131*e4b17023SJohn Marino instead of finding the basic block containing INSN, we search
132*e4b17023SJohn Marino backwards toward a BARRIER where the live register information is
133*e4b17023SJohn Marino correct. */
134*e4b17023SJohn Marino
135*e4b17023SJohn Marino static int
find_basic_block(rtx insn,int search_limit)136*e4b17023SJohn Marino find_basic_block (rtx insn, int search_limit)
137*e4b17023SJohn Marino {
138*e4b17023SJohn Marino /* Scan backwards to the previous BARRIER. Then see if we can find a
139*e4b17023SJohn Marino label that starts a basic block. Return the basic block number. */
140*e4b17023SJohn Marino for (insn = prev_nonnote_insn (insn);
141*e4b17023SJohn Marino insn && !BARRIER_P (insn) && search_limit != 0;
142*e4b17023SJohn Marino insn = prev_nonnote_insn (insn), --search_limit)
143*e4b17023SJohn Marino ;
144*e4b17023SJohn Marino
145*e4b17023SJohn Marino /* The closest BARRIER is too far away. */
146*e4b17023SJohn Marino if (search_limit == 0)
147*e4b17023SJohn Marino return -1;
148*e4b17023SJohn Marino
149*e4b17023SJohn Marino /* The start of the function. */
150*e4b17023SJohn Marino else if (insn == 0)
151*e4b17023SJohn Marino return ENTRY_BLOCK_PTR->next_bb->index;
152*e4b17023SJohn Marino
153*e4b17023SJohn Marino /* See if any of the upcoming CODE_LABELs start a basic block. If we reach
154*e4b17023SJohn Marino anything other than a CODE_LABEL or note, we can't find this code. */
155*e4b17023SJohn Marino for (insn = next_nonnote_insn (insn);
156*e4b17023SJohn Marino insn && LABEL_P (insn);
157*e4b17023SJohn Marino insn = next_nonnote_insn (insn))
158*e4b17023SJohn Marino if (BLOCK_FOR_INSN (insn))
159*e4b17023SJohn Marino return BLOCK_FOR_INSN (insn)->index;
160*e4b17023SJohn Marino
161*e4b17023SJohn Marino return -1;
162*e4b17023SJohn Marino }
163*e4b17023SJohn Marino
164*e4b17023SJohn Marino /* Similar to next_insn, but ignores insns in the delay slots of
165*e4b17023SJohn Marino an annulled branch. */
166*e4b17023SJohn Marino
167*e4b17023SJohn Marino static rtx
next_insn_no_annul(rtx insn)168*e4b17023SJohn Marino next_insn_no_annul (rtx insn)
169*e4b17023SJohn Marino {
170*e4b17023SJohn Marino if (insn)
171*e4b17023SJohn Marino {
172*e4b17023SJohn Marino /* If INSN is an annulled branch, skip any insns from the target
173*e4b17023SJohn Marino of the branch. */
174*e4b17023SJohn Marino if (JUMP_P (insn)
175*e4b17023SJohn Marino && INSN_ANNULLED_BRANCH_P (insn)
176*e4b17023SJohn Marino && NEXT_INSN (PREV_INSN (insn)) != insn)
177*e4b17023SJohn Marino {
178*e4b17023SJohn Marino rtx next = NEXT_INSN (insn);
179*e4b17023SJohn Marino enum rtx_code code = GET_CODE (next);
180*e4b17023SJohn Marino
181*e4b17023SJohn Marino while ((code == INSN || code == JUMP_INSN || code == CALL_INSN)
182*e4b17023SJohn Marino && INSN_FROM_TARGET_P (next))
183*e4b17023SJohn Marino {
184*e4b17023SJohn Marino insn = next;
185*e4b17023SJohn Marino next = NEXT_INSN (insn);
186*e4b17023SJohn Marino code = GET_CODE (next);
187*e4b17023SJohn Marino }
188*e4b17023SJohn Marino }
189*e4b17023SJohn Marino
190*e4b17023SJohn Marino insn = NEXT_INSN (insn);
191*e4b17023SJohn Marino if (insn && NONJUMP_INSN_P (insn)
192*e4b17023SJohn Marino && GET_CODE (PATTERN (insn)) == SEQUENCE)
193*e4b17023SJohn Marino insn = XVECEXP (PATTERN (insn), 0, 0);
194*e4b17023SJohn Marino }
195*e4b17023SJohn Marino
196*e4b17023SJohn Marino return insn;
197*e4b17023SJohn Marino }
198*e4b17023SJohn Marino
199*e4b17023SJohn Marino /* Given X, some rtl, and RES, a pointer to a `struct resource', mark
200*e4b17023SJohn Marino which resources are referenced by the insn. If INCLUDE_DELAYED_EFFECTS
201*e4b17023SJohn Marino is TRUE, resources used by the called routine will be included for
202*e4b17023SJohn Marino CALL_INSNs. */
203*e4b17023SJohn Marino
204*e4b17023SJohn Marino void
mark_referenced_resources(rtx x,struct resources * res,bool include_delayed_effects)205*e4b17023SJohn Marino mark_referenced_resources (rtx x, struct resources *res,
206*e4b17023SJohn Marino bool include_delayed_effects)
207*e4b17023SJohn Marino {
208*e4b17023SJohn Marino enum rtx_code code = GET_CODE (x);
209*e4b17023SJohn Marino int i, j;
210*e4b17023SJohn Marino unsigned int r;
211*e4b17023SJohn Marino const char *format_ptr;
212*e4b17023SJohn Marino
213*e4b17023SJohn Marino /* Handle leaf items for which we set resource flags. Also, special-case
214*e4b17023SJohn Marino CALL, SET and CLOBBER operators. */
215*e4b17023SJohn Marino switch (code)
216*e4b17023SJohn Marino {
217*e4b17023SJohn Marino case CONST:
218*e4b17023SJohn Marino case CONST_INT:
219*e4b17023SJohn Marino case CONST_DOUBLE:
220*e4b17023SJohn Marino case CONST_FIXED:
221*e4b17023SJohn Marino case CONST_VECTOR:
222*e4b17023SJohn Marino case PC:
223*e4b17023SJohn Marino case SYMBOL_REF:
224*e4b17023SJohn Marino case LABEL_REF:
225*e4b17023SJohn Marino return;
226*e4b17023SJohn Marino
227*e4b17023SJohn Marino case SUBREG:
228*e4b17023SJohn Marino if (!REG_P (SUBREG_REG (x)))
229*e4b17023SJohn Marino mark_referenced_resources (SUBREG_REG (x), res, false);
230*e4b17023SJohn Marino else
231*e4b17023SJohn Marino {
232*e4b17023SJohn Marino unsigned int regno = subreg_regno (x);
233*e4b17023SJohn Marino unsigned int last_regno = regno + subreg_nregs (x);
234*e4b17023SJohn Marino
235*e4b17023SJohn Marino gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER);
236*e4b17023SJohn Marino for (r = regno; r < last_regno; r++)
237*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, r);
238*e4b17023SJohn Marino }
239*e4b17023SJohn Marino return;
240*e4b17023SJohn Marino
241*e4b17023SJohn Marino case REG:
242*e4b17023SJohn Marino gcc_assert (HARD_REGISTER_P (x));
243*e4b17023SJohn Marino add_to_hard_reg_set (&res->regs, GET_MODE (x), REGNO (x));
244*e4b17023SJohn Marino return;
245*e4b17023SJohn Marino
246*e4b17023SJohn Marino case MEM:
247*e4b17023SJohn Marino /* If this memory shouldn't change, it really isn't referencing
248*e4b17023SJohn Marino memory. */
249*e4b17023SJohn Marino if (MEM_READONLY_P (x))
250*e4b17023SJohn Marino res->unch_memory = 1;
251*e4b17023SJohn Marino else
252*e4b17023SJohn Marino res->memory = 1;
253*e4b17023SJohn Marino res->volatil |= MEM_VOLATILE_P (x);
254*e4b17023SJohn Marino
255*e4b17023SJohn Marino /* Mark registers used to access memory. */
256*e4b17023SJohn Marino mark_referenced_resources (XEXP (x, 0), res, false);
257*e4b17023SJohn Marino return;
258*e4b17023SJohn Marino
259*e4b17023SJohn Marino case CC0:
260*e4b17023SJohn Marino res->cc = 1;
261*e4b17023SJohn Marino return;
262*e4b17023SJohn Marino
263*e4b17023SJohn Marino case UNSPEC_VOLATILE:
264*e4b17023SJohn Marino case TRAP_IF:
265*e4b17023SJohn Marino case ASM_INPUT:
266*e4b17023SJohn Marino /* Traditional asm's are always volatile. */
267*e4b17023SJohn Marino res->volatil = 1;
268*e4b17023SJohn Marino break;
269*e4b17023SJohn Marino
270*e4b17023SJohn Marino case ASM_OPERANDS:
271*e4b17023SJohn Marino res->volatil |= MEM_VOLATILE_P (x);
272*e4b17023SJohn Marino
273*e4b17023SJohn Marino /* For all ASM_OPERANDS, we must traverse the vector of input operands.
274*e4b17023SJohn Marino We can not just fall through here since then we would be confused
275*e4b17023SJohn Marino by the ASM_INPUT rtx inside ASM_OPERANDS, which do not indicate
276*e4b17023SJohn Marino traditional asms unlike their normal usage. */
277*e4b17023SJohn Marino
278*e4b17023SJohn Marino for (i = 0; i < ASM_OPERANDS_INPUT_LENGTH (x); i++)
279*e4b17023SJohn Marino mark_referenced_resources (ASM_OPERANDS_INPUT (x, i), res, false);
280*e4b17023SJohn Marino return;
281*e4b17023SJohn Marino
282*e4b17023SJohn Marino case CALL:
283*e4b17023SJohn Marino /* The first operand will be a (MEM (xxx)) but doesn't really reference
284*e4b17023SJohn Marino memory. The second operand may be referenced, though. */
285*e4b17023SJohn Marino mark_referenced_resources (XEXP (XEXP (x, 0), 0), res, false);
286*e4b17023SJohn Marino mark_referenced_resources (XEXP (x, 1), res, false);
287*e4b17023SJohn Marino return;
288*e4b17023SJohn Marino
289*e4b17023SJohn Marino case SET:
290*e4b17023SJohn Marino /* Usually, the first operand of SET is set, not referenced. But
291*e4b17023SJohn Marino registers used to access memory are referenced. SET_DEST is
292*e4b17023SJohn Marino also referenced if it is a ZERO_EXTRACT. */
293*e4b17023SJohn Marino
294*e4b17023SJohn Marino mark_referenced_resources (SET_SRC (x), res, false);
295*e4b17023SJohn Marino
296*e4b17023SJohn Marino x = SET_DEST (x);
297*e4b17023SJohn Marino if (GET_CODE (x) == ZERO_EXTRACT
298*e4b17023SJohn Marino || GET_CODE (x) == STRICT_LOW_PART)
299*e4b17023SJohn Marino mark_referenced_resources (x, res, false);
300*e4b17023SJohn Marino else if (GET_CODE (x) == SUBREG)
301*e4b17023SJohn Marino x = SUBREG_REG (x);
302*e4b17023SJohn Marino if (MEM_P (x))
303*e4b17023SJohn Marino mark_referenced_resources (XEXP (x, 0), res, false);
304*e4b17023SJohn Marino return;
305*e4b17023SJohn Marino
306*e4b17023SJohn Marino case CLOBBER:
307*e4b17023SJohn Marino return;
308*e4b17023SJohn Marino
309*e4b17023SJohn Marino case CALL_INSN:
310*e4b17023SJohn Marino if (include_delayed_effects)
311*e4b17023SJohn Marino {
312*e4b17023SJohn Marino /* A CALL references memory, the frame pointer if it exists, the
313*e4b17023SJohn Marino stack pointer, any global registers and any registers given in
314*e4b17023SJohn Marino USE insns immediately in front of the CALL.
315*e4b17023SJohn Marino
316*e4b17023SJohn Marino However, we may have moved some of the parameter loading insns
317*e4b17023SJohn Marino into the delay slot of this CALL. If so, the USE's for them
318*e4b17023SJohn Marino don't count and should be skipped. */
319*e4b17023SJohn Marino rtx insn = PREV_INSN (x);
320*e4b17023SJohn Marino rtx sequence = 0;
321*e4b17023SJohn Marino int seq_size = 0;
322*e4b17023SJohn Marino int i;
323*e4b17023SJohn Marino
324*e4b17023SJohn Marino /* If we are part of a delay slot sequence, point at the SEQUENCE. */
325*e4b17023SJohn Marino if (NEXT_INSN (insn) != x)
326*e4b17023SJohn Marino {
327*e4b17023SJohn Marino sequence = PATTERN (NEXT_INSN (insn));
328*e4b17023SJohn Marino seq_size = XVECLEN (sequence, 0);
329*e4b17023SJohn Marino gcc_assert (GET_CODE (sequence) == SEQUENCE);
330*e4b17023SJohn Marino }
331*e4b17023SJohn Marino
332*e4b17023SJohn Marino res->memory = 1;
333*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, STACK_POINTER_REGNUM);
334*e4b17023SJohn Marino if (frame_pointer_needed)
335*e4b17023SJohn Marino {
336*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, FRAME_POINTER_REGNUM);
337*e4b17023SJohn Marino #if !HARD_FRAME_POINTER_IS_FRAME_POINTER
338*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, HARD_FRAME_POINTER_REGNUM);
339*e4b17023SJohn Marino #endif
340*e4b17023SJohn Marino }
341*e4b17023SJohn Marino
342*e4b17023SJohn Marino for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
343*e4b17023SJohn Marino if (global_regs[i])
344*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, i);
345*e4b17023SJohn Marino
346*e4b17023SJohn Marino /* Check for a REG_SETJMP. If it exists, then we must
347*e4b17023SJohn Marino assume that this call can need any register.
348*e4b17023SJohn Marino
349*e4b17023SJohn Marino This is done to be more conservative about how we handle setjmp.
350*e4b17023SJohn Marino We assume that they both use and set all registers. Using all
351*e4b17023SJohn Marino registers ensures that a register will not be considered dead
352*e4b17023SJohn Marino just because it crosses a setjmp call. A register should be
353*e4b17023SJohn Marino considered dead only if the setjmp call returns nonzero. */
354*e4b17023SJohn Marino if (find_reg_note (x, REG_SETJMP, NULL))
355*e4b17023SJohn Marino SET_HARD_REG_SET (res->regs);
356*e4b17023SJohn Marino
357*e4b17023SJohn Marino {
358*e4b17023SJohn Marino rtx link;
359*e4b17023SJohn Marino
360*e4b17023SJohn Marino for (link = CALL_INSN_FUNCTION_USAGE (x);
361*e4b17023SJohn Marino link;
362*e4b17023SJohn Marino link = XEXP (link, 1))
363*e4b17023SJohn Marino if (GET_CODE (XEXP (link, 0)) == USE)
364*e4b17023SJohn Marino {
365*e4b17023SJohn Marino for (i = 1; i < seq_size; i++)
366*e4b17023SJohn Marino {
367*e4b17023SJohn Marino rtx slot_pat = PATTERN (XVECEXP (sequence, 0, i));
368*e4b17023SJohn Marino if (GET_CODE (slot_pat) == SET
369*e4b17023SJohn Marino && rtx_equal_p (SET_DEST (slot_pat),
370*e4b17023SJohn Marino XEXP (XEXP (link, 0), 0)))
371*e4b17023SJohn Marino break;
372*e4b17023SJohn Marino }
373*e4b17023SJohn Marino if (i >= seq_size)
374*e4b17023SJohn Marino mark_referenced_resources (XEXP (XEXP (link, 0), 0),
375*e4b17023SJohn Marino res, false);
376*e4b17023SJohn Marino }
377*e4b17023SJohn Marino }
378*e4b17023SJohn Marino }
379*e4b17023SJohn Marino
380*e4b17023SJohn Marino /* ... fall through to other INSN processing ... */
381*e4b17023SJohn Marino
382*e4b17023SJohn Marino case INSN:
383*e4b17023SJohn Marino case JUMP_INSN:
384*e4b17023SJohn Marino
385*e4b17023SJohn Marino #ifdef INSN_REFERENCES_ARE_DELAYED
386*e4b17023SJohn Marino if (! include_delayed_effects
387*e4b17023SJohn Marino && INSN_REFERENCES_ARE_DELAYED (x))
388*e4b17023SJohn Marino return;
389*e4b17023SJohn Marino #endif
390*e4b17023SJohn Marino
391*e4b17023SJohn Marino /* No special processing, just speed up. */
392*e4b17023SJohn Marino mark_referenced_resources (PATTERN (x), res, include_delayed_effects);
393*e4b17023SJohn Marino return;
394*e4b17023SJohn Marino
395*e4b17023SJohn Marino default:
396*e4b17023SJohn Marino break;
397*e4b17023SJohn Marino }
398*e4b17023SJohn Marino
399*e4b17023SJohn Marino /* Process each sub-expression and flag what it needs. */
400*e4b17023SJohn Marino format_ptr = GET_RTX_FORMAT (code);
401*e4b17023SJohn Marino for (i = 0; i < GET_RTX_LENGTH (code); i++)
402*e4b17023SJohn Marino switch (*format_ptr++)
403*e4b17023SJohn Marino {
404*e4b17023SJohn Marino case 'e':
405*e4b17023SJohn Marino mark_referenced_resources (XEXP (x, i), res, include_delayed_effects);
406*e4b17023SJohn Marino break;
407*e4b17023SJohn Marino
408*e4b17023SJohn Marino case 'E':
409*e4b17023SJohn Marino for (j = 0; j < XVECLEN (x, i); j++)
410*e4b17023SJohn Marino mark_referenced_resources (XVECEXP (x, i, j), res,
411*e4b17023SJohn Marino include_delayed_effects);
412*e4b17023SJohn Marino break;
413*e4b17023SJohn Marino }
414*e4b17023SJohn Marino }
415*e4b17023SJohn Marino
416*e4b17023SJohn Marino /* A subroutine of mark_target_live_regs. Search forward from TARGET
417*e4b17023SJohn Marino looking for registers that are set before they are used. These are dead.
418*e4b17023SJohn Marino Stop after passing a few conditional jumps, and/or a small
419*e4b17023SJohn Marino number of unconditional branches. */
420*e4b17023SJohn Marino
421*e4b17023SJohn Marino static rtx
find_dead_or_set_registers(rtx target,struct resources * res,rtx * jump_target,int jump_count,struct resources set,struct resources needed)422*e4b17023SJohn Marino find_dead_or_set_registers (rtx target, struct resources *res,
423*e4b17023SJohn Marino rtx *jump_target, int jump_count,
424*e4b17023SJohn Marino struct resources set, struct resources needed)
425*e4b17023SJohn Marino {
426*e4b17023SJohn Marino HARD_REG_SET scratch;
427*e4b17023SJohn Marino rtx insn, next;
428*e4b17023SJohn Marino rtx jump_insn = 0;
429*e4b17023SJohn Marino int i;
430*e4b17023SJohn Marino
431*e4b17023SJohn Marino for (insn = target; insn; insn = next)
432*e4b17023SJohn Marino {
433*e4b17023SJohn Marino rtx this_jump_insn = insn;
434*e4b17023SJohn Marino
435*e4b17023SJohn Marino next = NEXT_INSN (insn);
436*e4b17023SJohn Marino
437*e4b17023SJohn Marino /* If this instruction can throw an exception, then we don't
438*e4b17023SJohn Marino know where we might end up next. That means that we have to
439*e4b17023SJohn Marino assume that whatever we have already marked as live really is
440*e4b17023SJohn Marino live. */
441*e4b17023SJohn Marino if (can_throw_internal (insn))
442*e4b17023SJohn Marino break;
443*e4b17023SJohn Marino
444*e4b17023SJohn Marino switch (GET_CODE (insn))
445*e4b17023SJohn Marino {
446*e4b17023SJohn Marino case CODE_LABEL:
447*e4b17023SJohn Marino /* After a label, any pending dead registers that weren't yet
448*e4b17023SJohn Marino used can be made dead. */
449*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (pending_dead_regs, needed.regs);
450*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (res->regs, pending_dead_regs);
451*e4b17023SJohn Marino CLEAR_HARD_REG_SET (pending_dead_regs);
452*e4b17023SJohn Marino
453*e4b17023SJohn Marino continue;
454*e4b17023SJohn Marino
455*e4b17023SJohn Marino case BARRIER:
456*e4b17023SJohn Marino case NOTE:
457*e4b17023SJohn Marino continue;
458*e4b17023SJohn Marino
459*e4b17023SJohn Marino case INSN:
460*e4b17023SJohn Marino if (GET_CODE (PATTERN (insn)) == USE)
461*e4b17023SJohn Marino {
462*e4b17023SJohn Marino /* If INSN is a USE made by update_block, we care about the
463*e4b17023SJohn Marino underlying insn. Any registers set by the underlying insn
464*e4b17023SJohn Marino are live since the insn is being done somewhere else. */
465*e4b17023SJohn Marino if (INSN_P (XEXP (PATTERN (insn), 0)))
466*e4b17023SJohn Marino mark_set_resources (XEXP (PATTERN (insn), 0), res, 0,
467*e4b17023SJohn Marino MARK_SRC_DEST_CALL);
468*e4b17023SJohn Marino
469*e4b17023SJohn Marino /* All other USE insns are to be ignored. */
470*e4b17023SJohn Marino continue;
471*e4b17023SJohn Marino }
472*e4b17023SJohn Marino else if (GET_CODE (PATTERN (insn)) == CLOBBER)
473*e4b17023SJohn Marino continue;
474*e4b17023SJohn Marino else if (GET_CODE (PATTERN (insn)) == SEQUENCE)
475*e4b17023SJohn Marino {
476*e4b17023SJohn Marino /* An unconditional jump can be used to fill the delay slot
477*e4b17023SJohn Marino of a call, so search for a JUMP_INSN in any position. */
478*e4b17023SJohn Marino for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++)
479*e4b17023SJohn Marino {
480*e4b17023SJohn Marino this_jump_insn = XVECEXP (PATTERN (insn), 0, i);
481*e4b17023SJohn Marino if (JUMP_P (this_jump_insn))
482*e4b17023SJohn Marino break;
483*e4b17023SJohn Marino }
484*e4b17023SJohn Marino }
485*e4b17023SJohn Marino
486*e4b17023SJohn Marino default:
487*e4b17023SJohn Marino break;
488*e4b17023SJohn Marino }
489*e4b17023SJohn Marino
490*e4b17023SJohn Marino if (JUMP_P (this_jump_insn))
491*e4b17023SJohn Marino {
492*e4b17023SJohn Marino if (jump_count++ < 10)
493*e4b17023SJohn Marino {
494*e4b17023SJohn Marino if (any_uncondjump_p (this_jump_insn)
495*e4b17023SJohn Marino || ANY_RETURN_P (PATTERN (this_jump_insn)))
496*e4b17023SJohn Marino {
497*e4b17023SJohn Marino next = JUMP_LABEL (this_jump_insn);
498*e4b17023SJohn Marino if (ANY_RETURN_P (next))
499*e4b17023SJohn Marino next = NULL_RTX;
500*e4b17023SJohn Marino if (jump_insn == 0)
501*e4b17023SJohn Marino {
502*e4b17023SJohn Marino jump_insn = insn;
503*e4b17023SJohn Marino if (jump_target)
504*e4b17023SJohn Marino *jump_target = JUMP_LABEL (this_jump_insn);
505*e4b17023SJohn Marino }
506*e4b17023SJohn Marino }
507*e4b17023SJohn Marino else if (any_condjump_p (this_jump_insn))
508*e4b17023SJohn Marino {
509*e4b17023SJohn Marino struct resources target_set, target_res;
510*e4b17023SJohn Marino struct resources fallthrough_res;
511*e4b17023SJohn Marino
512*e4b17023SJohn Marino /* We can handle conditional branches here by following
513*e4b17023SJohn Marino both paths, and then IOR the results of the two paths
514*e4b17023SJohn Marino together, which will give us registers that are dead
515*e4b17023SJohn Marino on both paths. Since this is expensive, we give it
516*e4b17023SJohn Marino a much higher cost than unconditional branches. The
517*e4b17023SJohn Marino cost was chosen so that we will follow at most 1
518*e4b17023SJohn Marino conditional branch. */
519*e4b17023SJohn Marino
520*e4b17023SJohn Marino jump_count += 4;
521*e4b17023SJohn Marino if (jump_count >= 10)
522*e4b17023SJohn Marino break;
523*e4b17023SJohn Marino
524*e4b17023SJohn Marino mark_referenced_resources (insn, &needed, true);
525*e4b17023SJohn Marino
526*e4b17023SJohn Marino /* For an annulled branch, mark_set_resources ignores slots
527*e4b17023SJohn Marino filled by instructions from the target. This is correct
528*e4b17023SJohn Marino if the branch is not taken. Since we are following both
529*e4b17023SJohn Marino paths from the branch, we must also compute correct info
530*e4b17023SJohn Marino if the branch is taken. We do this by inverting all of
531*e4b17023SJohn Marino the INSN_FROM_TARGET_P bits, calling mark_set_resources,
532*e4b17023SJohn Marino and then inverting the INSN_FROM_TARGET_P bits again. */
533*e4b17023SJohn Marino
534*e4b17023SJohn Marino if (GET_CODE (PATTERN (insn)) == SEQUENCE
535*e4b17023SJohn Marino && INSN_ANNULLED_BRANCH_P (this_jump_insn))
536*e4b17023SJohn Marino {
537*e4b17023SJohn Marino for (i = 1; i < XVECLEN (PATTERN (insn), 0); i++)
538*e4b17023SJohn Marino INSN_FROM_TARGET_P (XVECEXP (PATTERN (insn), 0, i))
539*e4b17023SJohn Marino = ! INSN_FROM_TARGET_P (XVECEXP (PATTERN (insn), 0, i));
540*e4b17023SJohn Marino
541*e4b17023SJohn Marino target_set = set;
542*e4b17023SJohn Marino mark_set_resources (insn, &target_set, 0,
543*e4b17023SJohn Marino MARK_SRC_DEST_CALL);
544*e4b17023SJohn Marino
545*e4b17023SJohn Marino for (i = 1; i < XVECLEN (PATTERN (insn), 0); i++)
546*e4b17023SJohn Marino INSN_FROM_TARGET_P (XVECEXP (PATTERN (insn), 0, i))
547*e4b17023SJohn Marino = ! INSN_FROM_TARGET_P (XVECEXP (PATTERN (insn), 0, i));
548*e4b17023SJohn Marino
549*e4b17023SJohn Marino mark_set_resources (insn, &set, 0, MARK_SRC_DEST_CALL);
550*e4b17023SJohn Marino }
551*e4b17023SJohn Marino else
552*e4b17023SJohn Marino {
553*e4b17023SJohn Marino mark_set_resources (insn, &set, 0, MARK_SRC_DEST_CALL);
554*e4b17023SJohn Marino target_set = set;
555*e4b17023SJohn Marino }
556*e4b17023SJohn Marino
557*e4b17023SJohn Marino target_res = *res;
558*e4b17023SJohn Marino COPY_HARD_REG_SET (scratch, target_set.regs);
559*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (scratch, needed.regs);
560*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (target_res.regs, scratch);
561*e4b17023SJohn Marino
562*e4b17023SJohn Marino fallthrough_res = *res;
563*e4b17023SJohn Marino COPY_HARD_REG_SET (scratch, set.regs);
564*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (scratch, needed.regs);
565*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (fallthrough_res.regs, scratch);
566*e4b17023SJohn Marino
567*e4b17023SJohn Marino if (!ANY_RETURN_P (JUMP_LABEL (this_jump_insn)))
568*e4b17023SJohn Marino find_dead_or_set_registers (JUMP_LABEL (this_jump_insn),
569*e4b17023SJohn Marino &target_res, 0, jump_count,
570*e4b17023SJohn Marino target_set, needed);
571*e4b17023SJohn Marino find_dead_or_set_registers (next,
572*e4b17023SJohn Marino &fallthrough_res, 0, jump_count,
573*e4b17023SJohn Marino set, needed);
574*e4b17023SJohn Marino IOR_HARD_REG_SET (fallthrough_res.regs, target_res.regs);
575*e4b17023SJohn Marino AND_HARD_REG_SET (res->regs, fallthrough_res.regs);
576*e4b17023SJohn Marino break;
577*e4b17023SJohn Marino }
578*e4b17023SJohn Marino else
579*e4b17023SJohn Marino break;
580*e4b17023SJohn Marino }
581*e4b17023SJohn Marino else
582*e4b17023SJohn Marino {
583*e4b17023SJohn Marino /* Don't try this optimization if we expired our jump count
584*e4b17023SJohn Marino above, since that would mean there may be an infinite loop
585*e4b17023SJohn Marino in the function being compiled. */
586*e4b17023SJohn Marino jump_insn = 0;
587*e4b17023SJohn Marino break;
588*e4b17023SJohn Marino }
589*e4b17023SJohn Marino }
590*e4b17023SJohn Marino
591*e4b17023SJohn Marino mark_referenced_resources (insn, &needed, true);
592*e4b17023SJohn Marino mark_set_resources (insn, &set, 0, MARK_SRC_DEST_CALL);
593*e4b17023SJohn Marino
594*e4b17023SJohn Marino COPY_HARD_REG_SET (scratch, set.regs);
595*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (scratch, needed.regs);
596*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (res->regs, scratch);
597*e4b17023SJohn Marino }
598*e4b17023SJohn Marino
599*e4b17023SJohn Marino return jump_insn;
600*e4b17023SJohn Marino }
601*e4b17023SJohn Marino
602*e4b17023SJohn Marino /* Given X, a part of an insn, and a pointer to a `struct resource',
603*e4b17023SJohn Marino RES, indicate which resources are modified by the insn. If
604*e4b17023SJohn Marino MARK_TYPE is MARK_SRC_DEST_CALL, also mark resources potentially
605*e4b17023SJohn Marino set by the called routine.
606*e4b17023SJohn Marino
607*e4b17023SJohn Marino If IN_DEST is nonzero, it means we are inside a SET. Otherwise,
608*e4b17023SJohn Marino objects are being referenced instead of set.
609*e4b17023SJohn Marino
610*e4b17023SJohn Marino We never mark the insn as modifying the condition code unless it explicitly
611*e4b17023SJohn Marino SETs CC0 even though this is not totally correct. The reason for this is
612*e4b17023SJohn Marino that we require a SET of CC0 to immediately precede the reference to CC0.
613*e4b17023SJohn Marino So if some other insn sets CC0 as a side-effect, we know it cannot affect
614*e4b17023SJohn Marino our computation and thus may be placed in a delay slot. */
615*e4b17023SJohn Marino
616*e4b17023SJohn Marino void
mark_set_resources(rtx x,struct resources * res,int in_dest,enum mark_resource_type mark_type)617*e4b17023SJohn Marino mark_set_resources (rtx x, struct resources *res, int in_dest,
618*e4b17023SJohn Marino enum mark_resource_type mark_type)
619*e4b17023SJohn Marino {
620*e4b17023SJohn Marino enum rtx_code code;
621*e4b17023SJohn Marino int i, j;
622*e4b17023SJohn Marino unsigned int r;
623*e4b17023SJohn Marino const char *format_ptr;
624*e4b17023SJohn Marino
625*e4b17023SJohn Marino restart:
626*e4b17023SJohn Marino
627*e4b17023SJohn Marino code = GET_CODE (x);
628*e4b17023SJohn Marino
629*e4b17023SJohn Marino switch (code)
630*e4b17023SJohn Marino {
631*e4b17023SJohn Marino case NOTE:
632*e4b17023SJohn Marino case BARRIER:
633*e4b17023SJohn Marino case CODE_LABEL:
634*e4b17023SJohn Marino case USE:
635*e4b17023SJohn Marino case CONST_INT:
636*e4b17023SJohn Marino case CONST_DOUBLE:
637*e4b17023SJohn Marino case CONST_FIXED:
638*e4b17023SJohn Marino case CONST_VECTOR:
639*e4b17023SJohn Marino case LABEL_REF:
640*e4b17023SJohn Marino case SYMBOL_REF:
641*e4b17023SJohn Marino case CONST:
642*e4b17023SJohn Marino case PC:
643*e4b17023SJohn Marino /* These don't set any resources. */
644*e4b17023SJohn Marino return;
645*e4b17023SJohn Marino
646*e4b17023SJohn Marino case CC0:
647*e4b17023SJohn Marino if (in_dest)
648*e4b17023SJohn Marino res->cc = 1;
649*e4b17023SJohn Marino return;
650*e4b17023SJohn Marino
651*e4b17023SJohn Marino case CALL_INSN:
652*e4b17023SJohn Marino /* Called routine modifies the condition code, memory, any registers
653*e4b17023SJohn Marino that aren't saved across calls, global registers and anything
654*e4b17023SJohn Marino explicitly CLOBBERed immediately after the CALL_INSN. */
655*e4b17023SJohn Marino
656*e4b17023SJohn Marino if (mark_type == MARK_SRC_DEST_CALL)
657*e4b17023SJohn Marino {
658*e4b17023SJohn Marino rtx link;
659*e4b17023SJohn Marino
660*e4b17023SJohn Marino res->cc = res->memory = 1;
661*e4b17023SJohn Marino
662*e4b17023SJohn Marino IOR_HARD_REG_SET (res->regs, regs_invalidated_by_call);
663*e4b17023SJohn Marino
664*e4b17023SJohn Marino for (link = CALL_INSN_FUNCTION_USAGE (x);
665*e4b17023SJohn Marino link; link = XEXP (link, 1))
666*e4b17023SJohn Marino if (GET_CODE (XEXP (link, 0)) == CLOBBER)
667*e4b17023SJohn Marino mark_set_resources (SET_DEST (XEXP (link, 0)), res, 1,
668*e4b17023SJohn Marino MARK_SRC_DEST);
669*e4b17023SJohn Marino
670*e4b17023SJohn Marino /* Check for a REG_SETJMP. If it exists, then we must
671*e4b17023SJohn Marino assume that this call can clobber any register. */
672*e4b17023SJohn Marino if (find_reg_note (x, REG_SETJMP, NULL))
673*e4b17023SJohn Marino SET_HARD_REG_SET (res->regs);
674*e4b17023SJohn Marino }
675*e4b17023SJohn Marino
676*e4b17023SJohn Marino /* ... and also what its RTL says it modifies, if anything. */
677*e4b17023SJohn Marino
678*e4b17023SJohn Marino case JUMP_INSN:
679*e4b17023SJohn Marino case INSN:
680*e4b17023SJohn Marino
681*e4b17023SJohn Marino /* An insn consisting of just a CLOBBER (or USE) is just for flow
682*e4b17023SJohn Marino and doesn't actually do anything, so we ignore it. */
683*e4b17023SJohn Marino
684*e4b17023SJohn Marino #ifdef INSN_SETS_ARE_DELAYED
685*e4b17023SJohn Marino if (mark_type != MARK_SRC_DEST_CALL
686*e4b17023SJohn Marino && INSN_SETS_ARE_DELAYED (x))
687*e4b17023SJohn Marino return;
688*e4b17023SJohn Marino #endif
689*e4b17023SJohn Marino
690*e4b17023SJohn Marino x = PATTERN (x);
691*e4b17023SJohn Marino if (GET_CODE (x) != USE && GET_CODE (x) != CLOBBER)
692*e4b17023SJohn Marino goto restart;
693*e4b17023SJohn Marino return;
694*e4b17023SJohn Marino
695*e4b17023SJohn Marino case SET:
696*e4b17023SJohn Marino /* If the source of a SET is a CALL, this is actually done by
697*e4b17023SJohn Marino the called routine. So only include it if we are to include the
698*e4b17023SJohn Marino effects of the calling routine. */
699*e4b17023SJohn Marino
700*e4b17023SJohn Marino mark_set_resources (SET_DEST (x), res,
701*e4b17023SJohn Marino (mark_type == MARK_SRC_DEST_CALL
702*e4b17023SJohn Marino || GET_CODE (SET_SRC (x)) != CALL),
703*e4b17023SJohn Marino mark_type);
704*e4b17023SJohn Marino
705*e4b17023SJohn Marino mark_set_resources (SET_SRC (x), res, 0, MARK_SRC_DEST);
706*e4b17023SJohn Marino return;
707*e4b17023SJohn Marino
708*e4b17023SJohn Marino case CLOBBER:
709*e4b17023SJohn Marino mark_set_resources (XEXP (x, 0), res, 1, MARK_SRC_DEST);
710*e4b17023SJohn Marino return;
711*e4b17023SJohn Marino
712*e4b17023SJohn Marino case SEQUENCE:
713*e4b17023SJohn Marino {
714*e4b17023SJohn Marino rtx control = XVECEXP (x, 0, 0);
715*e4b17023SJohn Marino bool annul_p = JUMP_P (control) && INSN_ANNULLED_BRANCH_P (control);
716*e4b17023SJohn Marino
717*e4b17023SJohn Marino mark_set_resources (control, res, 0, mark_type);
718*e4b17023SJohn Marino for (i = XVECLEN (x, 0) - 1; i >= 0; --i)
719*e4b17023SJohn Marino {
720*e4b17023SJohn Marino rtx elt = XVECEXP (x, 0, i);
721*e4b17023SJohn Marino if (!annul_p && INSN_FROM_TARGET_P (elt))
722*e4b17023SJohn Marino mark_set_resources (elt, res, 0, mark_type);
723*e4b17023SJohn Marino }
724*e4b17023SJohn Marino }
725*e4b17023SJohn Marino return;
726*e4b17023SJohn Marino
727*e4b17023SJohn Marino case POST_INC:
728*e4b17023SJohn Marino case PRE_INC:
729*e4b17023SJohn Marino case POST_DEC:
730*e4b17023SJohn Marino case PRE_DEC:
731*e4b17023SJohn Marino mark_set_resources (XEXP (x, 0), res, 1, MARK_SRC_DEST);
732*e4b17023SJohn Marino return;
733*e4b17023SJohn Marino
734*e4b17023SJohn Marino case PRE_MODIFY:
735*e4b17023SJohn Marino case POST_MODIFY:
736*e4b17023SJohn Marino mark_set_resources (XEXP (x, 0), res, 1, MARK_SRC_DEST);
737*e4b17023SJohn Marino mark_set_resources (XEXP (XEXP (x, 1), 0), res, 0, MARK_SRC_DEST);
738*e4b17023SJohn Marino mark_set_resources (XEXP (XEXP (x, 1), 1), res, 0, MARK_SRC_DEST);
739*e4b17023SJohn Marino return;
740*e4b17023SJohn Marino
741*e4b17023SJohn Marino case SIGN_EXTRACT:
742*e4b17023SJohn Marino case ZERO_EXTRACT:
743*e4b17023SJohn Marino mark_set_resources (XEXP (x, 0), res, in_dest, MARK_SRC_DEST);
744*e4b17023SJohn Marino mark_set_resources (XEXP (x, 1), res, 0, MARK_SRC_DEST);
745*e4b17023SJohn Marino mark_set_resources (XEXP (x, 2), res, 0, MARK_SRC_DEST);
746*e4b17023SJohn Marino return;
747*e4b17023SJohn Marino
748*e4b17023SJohn Marino case MEM:
749*e4b17023SJohn Marino if (in_dest)
750*e4b17023SJohn Marino {
751*e4b17023SJohn Marino res->memory = 1;
752*e4b17023SJohn Marino res->unch_memory |= MEM_READONLY_P (x);
753*e4b17023SJohn Marino res->volatil |= MEM_VOLATILE_P (x);
754*e4b17023SJohn Marino }
755*e4b17023SJohn Marino
756*e4b17023SJohn Marino mark_set_resources (XEXP (x, 0), res, 0, MARK_SRC_DEST);
757*e4b17023SJohn Marino return;
758*e4b17023SJohn Marino
759*e4b17023SJohn Marino case SUBREG:
760*e4b17023SJohn Marino if (in_dest)
761*e4b17023SJohn Marino {
762*e4b17023SJohn Marino if (!REG_P (SUBREG_REG (x)))
763*e4b17023SJohn Marino mark_set_resources (SUBREG_REG (x), res, in_dest, mark_type);
764*e4b17023SJohn Marino else
765*e4b17023SJohn Marino {
766*e4b17023SJohn Marino unsigned int regno = subreg_regno (x);
767*e4b17023SJohn Marino unsigned int last_regno = regno + subreg_nregs (x);
768*e4b17023SJohn Marino
769*e4b17023SJohn Marino gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER);
770*e4b17023SJohn Marino for (r = regno; r < last_regno; r++)
771*e4b17023SJohn Marino SET_HARD_REG_BIT (res->regs, r);
772*e4b17023SJohn Marino }
773*e4b17023SJohn Marino }
774*e4b17023SJohn Marino return;
775*e4b17023SJohn Marino
776*e4b17023SJohn Marino case REG:
777*e4b17023SJohn Marino if (in_dest)
778*e4b17023SJohn Marino {
779*e4b17023SJohn Marino gcc_assert (HARD_REGISTER_P (x));
780*e4b17023SJohn Marino add_to_hard_reg_set (&res->regs, GET_MODE (x), REGNO (x));
781*e4b17023SJohn Marino }
782*e4b17023SJohn Marino return;
783*e4b17023SJohn Marino
784*e4b17023SJohn Marino case UNSPEC_VOLATILE:
785*e4b17023SJohn Marino case ASM_INPUT:
786*e4b17023SJohn Marino /* Traditional asm's are always volatile. */
787*e4b17023SJohn Marino res->volatil = 1;
788*e4b17023SJohn Marino return;
789*e4b17023SJohn Marino
790*e4b17023SJohn Marino case TRAP_IF:
791*e4b17023SJohn Marino res->volatil = 1;
792*e4b17023SJohn Marino break;
793*e4b17023SJohn Marino
794*e4b17023SJohn Marino case ASM_OPERANDS:
795*e4b17023SJohn Marino res->volatil |= MEM_VOLATILE_P (x);
796*e4b17023SJohn Marino
797*e4b17023SJohn Marino /* For all ASM_OPERANDS, we must traverse the vector of input operands.
798*e4b17023SJohn Marino We can not just fall through here since then we would be confused
799*e4b17023SJohn Marino by the ASM_INPUT rtx inside ASM_OPERANDS, which do not indicate
800*e4b17023SJohn Marino traditional asms unlike their normal usage. */
801*e4b17023SJohn Marino
802*e4b17023SJohn Marino for (i = 0; i < ASM_OPERANDS_INPUT_LENGTH (x); i++)
803*e4b17023SJohn Marino mark_set_resources (ASM_OPERANDS_INPUT (x, i), res, in_dest,
804*e4b17023SJohn Marino MARK_SRC_DEST);
805*e4b17023SJohn Marino return;
806*e4b17023SJohn Marino
807*e4b17023SJohn Marino default:
808*e4b17023SJohn Marino break;
809*e4b17023SJohn Marino }
810*e4b17023SJohn Marino
811*e4b17023SJohn Marino /* Process each sub-expression and flag what it needs. */
812*e4b17023SJohn Marino format_ptr = GET_RTX_FORMAT (code);
813*e4b17023SJohn Marino for (i = 0; i < GET_RTX_LENGTH (code); i++)
814*e4b17023SJohn Marino switch (*format_ptr++)
815*e4b17023SJohn Marino {
816*e4b17023SJohn Marino case 'e':
817*e4b17023SJohn Marino mark_set_resources (XEXP (x, i), res, in_dest, mark_type);
818*e4b17023SJohn Marino break;
819*e4b17023SJohn Marino
820*e4b17023SJohn Marino case 'E':
821*e4b17023SJohn Marino for (j = 0; j < XVECLEN (x, i); j++)
822*e4b17023SJohn Marino mark_set_resources (XVECEXP (x, i, j), res, in_dest, mark_type);
823*e4b17023SJohn Marino break;
824*e4b17023SJohn Marino }
825*e4b17023SJohn Marino }
826*e4b17023SJohn Marino
827*e4b17023SJohn Marino /* Return TRUE if INSN is a return, possibly with a filled delay slot. */
828*e4b17023SJohn Marino
829*e4b17023SJohn Marino static bool
return_insn_p(const_rtx insn)830*e4b17023SJohn Marino return_insn_p (const_rtx insn)
831*e4b17023SJohn Marino {
832*e4b17023SJohn Marino if (JUMP_P (insn) && ANY_RETURN_P (PATTERN (insn)))
833*e4b17023SJohn Marino return true;
834*e4b17023SJohn Marino
835*e4b17023SJohn Marino if (NONJUMP_INSN_P (insn) && GET_CODE (PATTERN (insn)) == SEQUENCE)
836*e4b17023SJohn Marino return return_insn_p (XVECEXP (PATTERN (insn), 0, 0));
837*e4b17023SJohn Marino
838*e4b17023SJohn Marino return false;
839*e4b17023SJohn Marino }
840*e4b17023SJohn Marino
841*e4b17023SJohn Marino /* Set the resources that are live at TARGET.
842*e4b17023SJohn Marino
843*e4b17023SJohn Marino If TARGET is zero, we refer to the end of the current function and can
844*e4b17023SJohn Marino return our precomputed value.
845*e4b17023SJohn Marino
846*e4b17023SJohn Marino Otherwise, we try to find out what is live by consulting the basic block
847*e4b17023SJohn Marino information. This is tricky, because we must consider the actions of
848*e4b17023SJohn Marino reload and jump optimization, which occur after the basic block information
849*e4b17023SJohn Marino has been computed.
850*e4b17023SJohn Marino
851*e4b17023SJohn Marino Accordingly, we proceed as follows::
852*e4b17023SJohn Marino
853*e4b17023SJohn Marino We find the previous BARRIER and look at all immediately following labels
854*e4b17023SJohn Marino (with no intervening active insns) to see if any of them start a basic
855*e4b17023SJohn Marino block. If we hit the start of the function first, we use block 0.
856*e4b17023SJohn Marino
857*e4b17023SJohn Marino Once we have found a basic block and a corresponding first insn, we can
858*e4b17023SJohn Marino accurately compute the live status (by starting at a label following a
859*e4b17023SJohn Marino BARRIER, we are immune to actions taken by reload and jump.) Then we
860*e4b17023SJohn Marino scan all insns between that point and our target. For each CLOBBER (or
861*e4b17023SJohn Marino for call-clobbered regs when we pass a CALL_INSN), mark the appropriate
862*e4b17023SJohn Marino registers are dead. For a SET, mark them as live.
863*e4b17023SJohn Marino
864*e4b17023SJohn Marino We have to be careful when using REG_DEAD notes because they are not
865*e4b17023SJohn Marino updated by such things as find_equiv_reg. So keep track of registers
866*e4b17023SJohn Marino marked as dead that haven't been assigned to, and mark them dead at the
867*e4b17023SJohn Marino next CODE_LABEL since reload and jump won't propagate values across labels.
868*e4b17023SJohn Marino
869*e4b17023SJohn Marino If we cannot find the start of a basic block (should be a very rare
870*e4b17023SJohn Marino case, if it can happen at all), mark everything as potentially live.
871*e4b17023SJohn Marino
872*e4b17023SJohn Marino Next, scan forward from TARGET looking for things set or clobbered
873*e4b17023SJohn Marino before they are used. These are not live.
874*e4b17023SJohn Marino
875*e4b17023SJohn Marino Because we can be called many times on the same target, save our results
876*e4b17023SJohn Marino in a hash table indexed by INSN_UID. This is only done if the function
877*e4b17023SJohn Marino init_resource_info () was invoked before we are called. */
878*e4b17023SJohn Marino
879*e4b17023SJohn Marino void
mark_target_live_regs(rtx insns,rtx target,struct resources * res)880*e4b17023SJohn Marino mark_target_live_regs (rtx insns, rtx target, struct resources *res)
881*e4b17023SJohn Marino {
882*e4b17023SJohn Marino int b = -1;
883*e4b17023SJohn Marino unsigned int i;
884*e4b17023SJohn Marino struct target_info *tinfo = NULL;
885*e4b17023SJohn Marino rtx insn;
886*e4b17023SJohn Marino rtx jump_insn = 0;
887*e4b17023SJohn Marino rtx jump_target;
888*e4b17023SJohn Marino HARD_REG_SET scratch;
889*e4b17023SJohn Marino struct resources set, needed;
890*e4b17023SJohn Marino
891*e4b17023SJohn Marino /* Handle end of function. */
892*e4b17023SJohn Marino if (target == 0 || ANY_RETURN_P (target))
893*e4b17023SJohn Marino {
894*e4b17023SJohn Marino *res = end_of_function_needs;
895*e4b17023SJohn Marino return;
896*e4b17023SJohn Marino }
897*e4b17023SJohn Marino
898*e4b17023SJohn Marino /* Handle return insn. */
899*e4b17023SJohn Marino else if (return_insn_p (target))
900*e4b17023SJohn Marino {
901*e4b17023SJohn Marino *res = end_of_function_needs;
902*e4b17023SJohn Marino mark_referenced_resources (target, res, false);
903*e4b17023SJohn Marino return;
904*e4b17023SJohn Marino }
905*e4b17023SJohn Marino
906*e4b17023SJohn Marino /* We have to assume memory is needed, but the CC isn't. */
907*e4b17023SJohn Marino res->memory = 1;
908*e4b17023SJohn Marino res->volatil = res->unch_memory = 0;
909*e4b17023SJohn Marino res->cc = 0;
910*e4b17023SJohn Marino
911*e4b17023SJohn Marino /* See if we have computed this value already. */
912*e4b17023SJohn Marino if (target_hash_table != NULL)
913*e4b17023SJohn Marino {
914*e4b17023SJohn Marino for (tinfo = target_hash_table[INSN_UID (target) % TARGET_HASH_PRIME];
915*e4b17023SJohn Marino tinfo; tinfo = tinfo->next)
916*e4b17023SJohn Marino if (tinfo->uid == INSN_UID (target))
917*e4b17023SJohn Marino break;
918*e4b17023SJohn Marino
919*e4b17023SJohn Marino /* Start by getting the basic block number. If we have saved
920*e4b17023SJohn Marino information, we can get it from there unless the insn at the
921*e4b17023SJohn Marino start of the basic block has been deleted. */
922*e4b17023SJohn Marino if (tinfo && tinfo->block != -1
923*e4b17023SJohn Marino && ! INSN_DELETED_P (BB_HEAD (BASIC_BLOCK (tinfo->block))))
924*e4b17023SJohn Marino b = tinfo->block;
925*e4b17023SJohn Marino }
926*e4b17023SJohn Marino
927*e4b17023SJohn Marino if (b == -1)
928*e4b17023SJohn Marino b = find_basic_block (target, MAX_DELAY_SLOT_LIVE_SEARCH);
929*e4b17023SJohn Marino
930*e4b17023SJohn Marino if (target_hash_table != NULL)
931*e4b17023SJohn Marino {
932*e4b17023SJohn Marino if (tinfo)
933*e4b17023SJohn Marino {
934*e4b17023SJohn Marino /* If the information is up-to-date, use it. Otherwise, we will
935*e4b17023SJohn Marino update it below. */
936*e4b17023SJohn Marino if (b == tinfo->block && b != -1 && tinfo->bb_tick == bb_ticks[b])
937*e4b17023SJohn Marino {
938*e4b17023SJohn Marino COPY_HARD_REG_SET (res->regs, tinfo->live_regs);
939*e4b17023SJohn Marino return;
940*e4b17023SJohn Marino }
941*e4b17023SJohn Marino }
942*e4b17023SJohn Marino else
943*e4b17023SJohn Marino {
944*e4b17023SJohn Marino /* Allocate a place to put our results and chain it into the
945*e4b17023SJohn Marino hash table. */
946*e4b17023SJohn Marino tinfo = XNEW (struct target_info);
947*e4b17023SJohn Marino tinfo->uid = INSN_UID (target);
948*e4b17023SJohn Marino tinfo->block = b;
949*e4b17023SJohn Marino tinfo->next
950*e4b17023SJohn Marino = target_hash_table[INSN_UID (target) % TARGET_HASH_PRIME];
951*e4b17023SJohn Marino target_hash_table[INSN_UID (target) % TARGET_HASH_PRIME] = tinfo;
952*e4b17023SJohn Marino }
953*e4b17023SJohn Marino }
954*e4b17023SJohn Marino
955*e4b17023SJohn Marino CLEAR_HARD_REG_SET (pending_dead_regs);
956*e4b17023SJohn Marino
957*e4b17023SJohn Marino /* If we found a basic block, get the live registers from it and update
958*e4b17023SJohn Marino them with anything set or killed between its start and the insn before
959*e4b17023SJohn Marino TARGET; this custom life analysis is really about registers so we need
960*e4b17023SJohn Marino to use the LR problem. Otherwise, we must assume everything is live. */
961*e4b17023SJohn Marino if (b != -1)
962*e4b17023SJohn Marino {
963*e4b17023SJohn Marino regset regs_live = DF_LR_IN (BASIC_BLOCK (b));
964*e4b17023SJohn Marino rtx start_insn, stop_insn;
965*e4b17023SJohn Marino
966*e4b17023SJohn Marino /* Compute hard regs live at start of block. */
967*e4b17023SJohn Marino REG_SET_TO_HARD_REG_SET (current_live_regs, regs_live);
968*e4b17023SJohn Marino
969*e4b17023SJohn Marino /* Get starting and ending insn, handling the case where each might
970*e4b17023SJohn Marino be a SEQUENCE. */
971*e4b17023SJohn Marino start_insn = (b == ENTRY_BLOCK_PTR->next_bb->index ?
972*e4b17023SJohn Marino insns : BB_HEAD (BASIC_BLOCK (b)));
973*e4b17023SJohn Marino stop_insn = target;
974*e4b17023SJohn Marino
975*e4b17023SJohn Marino if (NONJUMP_INSN_P (start_insn)
976*e4b17023SJohn Marino && GET_CODE (PATTERN (start_insn)) == SEQUENCE)
977*e4b17023SJohn Marino start_insn = XVECEXP (PATTERN (start_insn), 0, 0);
978*e4b17023SJohn Marino
979*e4b17023SJohn Marino if (NONJUMP_INSN_P (stop_insn)
980*e4b17023SJohn Marino && GET_CODE (PATTERN (stop_insn)) == SEQUENCE)
981*e4b17023SJohn Marino stop_insn = next_insn (PREV_INSN (stop_insn));
982*e4b17023SJohn Marino
983*e4b17023SJohn Marino for (insn = start_insn; insn != stop_insn;
984*e4b17023SJohn Marino insn = next_insn_no_annul (insn))
985*e4b17023SJohn Marino {
986*e4b17023SJohn Marino rtx link;
987*e4b17023SJohn Marino rtx real_insn = insn;
988*e4b17023SJohn Marino enum rtx_code code = GET_CODE (insn);
989*e4b17023SJohn Marino
990*e4b17023SJohn Marino if (DEBUG_INSN_P (insn))
991*e4b17023SJohn Marino continue;
992*e4b17023SJohn Marino
993*e4b17023SJohn Marino /* If this insn is from the target of a branch, it isn't going to
994*e4b17023SJohn Marino be used in the sequel. If it is used in both cases, this
995*e4b17023SJohn Marino test will not be true. */
996*e4b17023SJohn Marino if ((code == INSN || code == JUMP_INSN || code == CALL_INSN)
997*e4b17023SJohn Marino && INSN_FROM_TARGET_P (insn))
998*e4b17023SJohn Marino continue;
999*e4b17023SJohn Marino
1000*e4b17023SJohn Marino /* If this insn is a USE made by update_block, we care about the
1001*e4b17023SJohn Marino underlying insn. */
1002*e4b17023SJohn Marino if (code == INSN && GET_CODE (PATTERN (insn)) == USE
1003*e4b17023SJohn Marino && INSN_P (XEXP (PATTERN (insn), 0)))
1004*e4b17023SJohn Marino real_insn = XEXP (PATTERN (insn), 0);
1005*e4b17023SJohn Marino
1006*e4b17023SJohn Marino if (CALL_P (real_insn))
1007*e4b17023SJohn Marino {
1008*e4b17023SJohn Marino /* CALL clobbers all call-used regs that aren't fixed except
1009*e4b17023SJohn Marino sp, ap, and fp. Do this before setting the result of the
1010*e4b17023SJohn Marino call live. */
1011*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (current_live_regs,
1012*e4b17023SJohn Marino regs_invalidated_by_call);
1013*e4b17023SJohn Marino
1014*e4b17023SJohn Marino /* A CALL_INSN sets any global register live, since it may
1015*e4b17023SJohn Marino have been modified by the call. */
1016*e4b17023SJohn Marino for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1017*e4b17023SJohn Marino if (global_regs[i])
1018*e4b17023SJohn Marino SET_HARD_REG_BIT (current_live_regs, i);
1019*e4b17023SJohn Marino }
1020*e4b17023SJohn Marino
1021*e4b17023SJohn Marino /* Mark anything killed in an insn to be deadened at the next
1022*e4b17023SJohn Marino label. Ignore USE insns; the only REG_DEAD notes will be for
1023*e4b17023SJohn Marino parameters. But they might be early. A CALL_INSN will usually
1024*e4b17023SJohn Marino clobber registers used for parameters. It isn't worth bothering
1025*e4b17023SJohn Marino with the unlikely case when it won't. */
1026*e4b17023SJohn Marino if ((NONJUMP_INSN_P (real_insn)
1027*e4b17023SJohn Marino && GET_CODE (PATTERN (real_insn)) != USE
1028*e4b17023SJohn Marino && GET_CODE (PATTERN (real_insn)) != CLOBBER)
1029*e4b17023SJohn Marino || JUMP_P (real_insn)
1030*e4b17023SJohn Marino || CALL_P (real_insn))
1031*e4b17023SJohn Marino {
1032*e4b17023SJohn Marino for (link = REG_NOTES (real_insn); link; link = XEXP (link, 1))
1033*e4b17023SJohn Marino if (REG_NOTE_KIND (link) == REG_DEAD
1034*e4b17023SJohn Marino && REG_P (XEXP (link, 0))
1035*e4b17023SJohn Marino && REGNO (XEXP (link, 0)) < FIRST_PSEUDO_REGISTER)
1036*e4b17023SJohn Marino add_to_hard_reg_set (&pending_dead_regs,
1037*e4b17023SJohn Marino GET_MODE (XEXP (link, 0)),
1038*e4b17023SJohn Marino REGNO (XEXP (link, 0)));
1039*e4b17023SJohn Marino
1040*e4b17023SJohn Marino note_stores (PATTERN (real_insn), update_live_status, NULL);
1041*e4b17023SJohn Marino
1042*e4b17023SJohn Marino /* If any registers were unused after this insn, kill them.
1043*e4b17023SJohn Marino These notes will always be accurate. */
1044*e4b17023SJohn Marino for (link = REG_NOTES (real_insn); link; link = XEXP (link, 1))
1045*e4b17023SJohn Marino if (REG_NOTE_KIND (link) == REG_UNUSED
1046*e4b17023SJohn Marino && REG_P (XEXP (link, 0))
1047*e4b17023SJohn Marino && REGNO (XEXP (link, 0)) < FIRST_PSEUDO_REGISTER)
1048*e4b17023SJohn Marino remove_from_hard_reg_set (¤t_live_regs,
1049*e4b17023SJohn Marino GET_MODE (XEXP (link, 0)),
1050*e4b17023SJohn Marino REGNO (XEXP (link, 0)));
1051*e4b17023SJohn Marino }
1052*e4b17023SJohn Marino
1053*e4b17023SJohn Marino else if (LABEL_P (real_insn))
1054*e4b17023SJohn Marino {
1055*e4b17023SJohn Marino basic_block bb;
1056*e4b17023SJohn Marino
1057*e4b17023SJohn Marino /* A label clobbers the pending dead registers since neither
1058*e4b17023SJohn Marino reload nor jump will propagate a value across a label. */
1059*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (current_live_regs, pending_dead_regs);
1060*e4b17023SJohn Marino CLEAR_HARD_REG_SET (pending_dead_regs);
1061*e4b17023SJohn Marino
1062*e4b17023SJohn Marino /* We must conservatively assume that all registers that used
1063*e4b17023SJohn Marino to be live here still are. The fallthrough edge may have
1064*e4b17023SJohn Marino left a live register uninitialized. */
1065*e4b17023SJohn Marino bb = BLOCK_FOR_INSN (real_insn);
1066*e4b17023SJohn Marino if (bb)
1067*e4b17023SJohn Marino {
1068*e4b17023SJohn Marino HARD_REG_SET extra_live;
1069*e4b17023SJohn Marino
1070*e4b17023SJohn Marino REG_SET_TO_HARD_REG_SET (extra_live, DF_LR_IN (bb));
1071*e4b17023SJohn Marino IOR_HARD_REG_SET (current_live_regs, extra_live);
1072*e4b17023SJohn Marino }
1073*e4b17023SJohn Marino }
1074*e4b17023SJohn Marino
1075*e4b17023SJohn Marino /* The beginning of the epilogue corresponds to the end of the
1076*e4b17023SJohn Marino RTL chain when there are no epilogue insns. Certain resources
1077*e4b17023SJohn Marino are implicitly required at that point. */
1078*e4b17023SJohn Marino else if (NOTE_P (real_insn)
1079*e4b17023SJohn Marino && NOTE_KIND (real_insn) == NOTE_INSN_EPILOGUE_BEG)
1080*e4b17023SJohn Marino IOR_HARD_REG_SET (current_live_regs, start_of_epilogue_needs.regs);
1081*e4b17023SJohn Marino }
1082*e4b17023SJohn Marino
1083*e4b17023SJohn Marino COPY_HARD_REG_SET (res->regs, current_live_regs);
1084*e4b17023SJohn Marino if (tinfo != NULL)
1085*e4b17023SJohn Marino {
1086*e4b17023SJohn Marino tinfo->block = b;
1087*e4b17023SJohn Marino tinfo->bb_tick = bb_ticks[b];
1088*e4b17023SJohn Marino }
1089*e4b17023SJohn Marino }
1090*e4b17023SJohn Marino else
1091*e4b17023SJohn Marino /* We didn't find the start of a basic block. Assume everything
1092*e4b17023SJohn Marino in use. This should happen only extremely rarely. */
1093*e4b17023SJohn Marino SET_HARD_REG_SET (res->regs);
1094*e4b17023SJohn Marino
1095*e4b17023SJohn Marino CLEAR_RESOURCE (&set);
1096*e4b17023SJohn Marino CLEAR_RESOURCE (&needed);
1097*e4b17023SJohn Marino
1098*e4b17023SJohn Marino jump_insn = find_dead_or_set_registers (target, res, &jump_target, 0,
1099*e4b17023SJohn Marino set, needed);
1100*e4b17023SJohn Marino
1101*e4b17023SJohn Marino /* If we hit an unconditional branch, we have another way of finding out
1102*e4b17023SJohn Marino what is live: we can see what is live at the branch target and include
1103*e4b17023SJohn Marino anything used but not set before the branch. We add the live
1104*e4b17023SJohn Marino resources found using the test below to those found until now. */
1105*e4b17023SJohn Marino
1106*e4b17023SJohn Marino if (jump_insn)
1107*e4b17023SJohn Marino {
1108*e4b17023SJohn Marino struct resources new_resources;
1109*e4b17023SJohn Marino rtx stop_insn = next_active_insn (jump_insn);
1110*e4b17023SJohn Marino
1111*e4b17023SJohn Marino if (!ANY_RETURN_P (jump_target))
1112*e4b17023SJohn Marino jump_target = next_active_insn (jump_target);
1113*e4b17023SJohn Marino mark_target_live_regs (insns, jump_target, &new_resources);
1114*e4b17023SJohn Marino CLEAR_RESOURCE (&set);
1115*e4b17023SJohn Marino CLEAR_RESOURCE (&needed);
1116*e4b17023SJohn Marino
1117*e4b17023SJohn Marino /* Include JUMP_INSN in the needed registers. */
1118*e4b17023SJohn Marino for (insn = target; insn != stop_insn; insn = next_active_insn (insn))
1119*e4b17023SJohn Marino {
1120*e4b17023SJohn Marino mark_referenced_resources (insn, &needed, true);
1121*e4b17023SJohn Marino
1122*e4b17023SJohn Marino COPY_HARD_REG_SET (scratch, needed.regs);
1123*e4b17023SJohn Marino AND_COMPL_HARD_REG_SET (scratch, set.regs);
1124*e4b17023SJohn Marino IOR_HARD_REG_SET (new_resources.regs, scratch);
1125*e4b17023SJohn Marino
1126*e4b17023SJohn Marino mark_set_resources (insn, &set, 0, MARK_SRC_DEST_CALL);
1127*e4b17023SJohn Marino }
1128*e4b17023SJohn Marino
1129*e4b17023SJohn Marino IOR_HARD_REG_SET (res->regs, new_resources.regs);
1130*e4b17023SJohn Marino }
1131*e4b17023SJohn Marino
1132*e4b17023SJohn Marino if (tinfo != NULL)
1133*e4b17023SJohn Marino {
1134*e4b17023SJohn Marino COPY_HARD_REG_SET (tinfo->live_regs, res->regs);
1135*e4b17023SJohn Marino }
1136*e4b17023SJohn Marino }
1137*e4b17023SJohn Marino
1138*e4b17023SJohn Marino /* Initialize the resources required by mark_target_live_regs ().
1139*e4b17023SJohn Marino This should be invoked before the first call to mark_target_live_regs. */
1140*e4b17023SJohn Marino
1141*e4b17023SJohn Marino void
init_resource_info(rtx epilogue_insn)1142*e4b17023SJohn Marino init_resource_info (rtx epilogue_insn)
1143*e4b17023SJohn Marino {
1144*e4b17023SJohn Marino int i;
1145*e4b17023SJohn Marino basic_block bb;
1146*e4b17023SJohn Marino
1147*e4b17023SJohn Marino /* Indicate what resources are required to be valid at the end of the current
1148*e4b17023SJohn Marino function. The condition code never is and memory always is.
1149*e4b17023SJohn Marino The stack pointer is needed unless EXIT_IGNORE_STACK is true
1150*e4b17023SJohn Marino and there is an epilogue that restores the original stack pointer
1151*e4b17023SJohn Marino from the frame pointer. Registers used to return the function value
1152*e4b17023SJohn Marino are needed. Registers holding global variables are needed. */
1153*e4b17023SJohn Marino
1154*e4b17023SJohn Marino end_of_function_needs.cc = 0;
1155*e4b17023SJohn Marino end_of_function_needs.memory = 1;
1156*e4b17023SJohn Marino end_of_function_needs.unch_memory = 0;
1157*e4b17023SJohn Marino CLEAR_HARD_REG_SET (end_of_function_needs.regs);
1158*e4b17023SJohn Marino
1159*e4b17023SJohn Marino if (frame_pointer_needed)
1160*e4b17023SJohn Marino {
1161*e4b17023SJohn Marino SET_HARD_REG_BIT (end_of_function_needs.regs, FRAME_POINTER_REGNUM);
1162*e4b17023SJohn Marino #if !HARD_FRAME_POINTER_IS_FRAME_POINTER
1163*e4b17023SJohn Marino SET_HARD_REG_BIT (end_of_function_needs.regs, HARD_FRAME_POINTER_REGNUM);
1164*e4b17023SJohn Marino #endif
1165*e4b17023SJohn Marino }
1166*e4b17023SJohn Marino if (!(frame_pointer_needed
1167*e4b17023SJohn Marino && EXIT_IGNORE_STACK
1168*e4b17023SJohn Marino && epilogue_insn
1169*e4b17023SJohn Marino && !current_function_sp_is_unchanging))
1170*e4b17023SJohn Marino SET_HARD_REG_BIT (end_of_function_needs.regs, STACK_POINTER_REGNUM);
1171*e4b17023SJohn Marino
1172*e4b17023SJohn Marino if (crtl->return_rtx != 0)
1173*e4b17023SJohn Marino mark_referenced_resources (crtl->return_rtx,
1174*e4b17023SJohn Marino &end_of_function_needs, true);
1175*e4b17023SJohn Marino
1176*e4b17023SJohn Marino for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1177*e4b17023SJohn Marino if (global_regs[i]
1178*e4b17023SJohn Marino #ifdef EPILOGUE_USES
1179*e4b17023SJohn Marino || EPILOGUE_USES (i)
1180*e4b17023SJohn Marino #endif
1181*e4b17023SJohn Marino )
1182*e4b17023SJohn Marino SET_HARD_REG_BIT (end_of_function_needs.regs, i);
1183*e4b17023SJohn Marino
1184*e4b17023SJohn Marino /* The registers required to be live at the end of the function are
1185*e4b17023SJohn Marino represented in the flow information as being dead just prior to
1186*e4b17023SJohn Marino reaching the end of the function. For example, the return of a value
1187*e4b17023SJohn Marino might be represented by a USE of the return register immediately
1188*e4b17023SJohn Marino followed by an unconditional jump to the return label where the
1189*e4b17023SJohn Marino return label is the end of the RTL chain. The end of the RTL chain
1190*e4b17023SJohn Marino is then taken to mean that the return register is live.
1191*e4b17023SJohn Marino
1192*e4b17023SJohn Marino This sequence is no longer maintained when epilogue instructions are
1193*e4b17023SJohn Marino added to the RTL chain. To reconstruct the original meaning, the
1194*e4b17023SJohn Marino start of the epilogue (NOTE_INSN_EPILOGUE_BEG) is regarded as the
1195*e4b17023SJohn Marino point where these registers become live (start_of_epilogue_needs).
1196*e4b17023SJohn Marino If epilogue instructions are present, the registers set by those
1197*e4b17023SJohn Marino instructions won't have been processed by flow. Thus, those
1198*e4b17023SJohn Marino registers are additionally required at the end of the RTL chain
1199*e4b17023SJohn Marino (end_of_function_needs). */
1200*e4b17023SJohn Marino
1201*e4b17023SJohn Marino start_of_epilogue_needs = end_of_function_needs;
1202*e4b17023SJohn Marino
1203*e4b17023SJohn Marino while ((epilogue_insn = next_nonnote_insn (epilogue_insn)))
1204*e4b17023SJohn Marino {
1205*e4b17023SJohn Marino mark_set_resources (epilogue_insn, &end_of_function_needs, 0,
1206*e4b17023SJohn Marino MARK_SRC_DEST_CALL);
1207*e4b17023SJohn Marino if (return_insn_p (epilogue_insn))
1208*e4b17023SJohn Marino break;
1209*e4b17023SJohn Marino }
1210*e4b17023SJohn Marino
1211*e4b17023SJohn Marino /* Allocate and initialize the tables used by mark_target_live_regs. */
1212*e4b17023SJohn Marino target_hash_table = XCNEWVEC (struct target_info *, TARGET_HASH_PRIME);
1213*e4b17023SJohn Marino bb_ticks = XCNEWVEC (int, last_basic_block);
1214*e4b17023SJohn Marino
1215*e4b17023SJohn Marino /* Set the BLOCK_FOR_INSN of each label that starts a basic block. */
1216*e4b17023SJohn Marino FOR_EACH_BB (bb)
1217*e4b17023SJohn Marino if (LABEL_P (BB_HEAD (bb)))
1218*e4b17023SJohn Marino BLOCK_FOR_INSN (BB_HEAD (bb)) = bb;
1219*e4b17023SJohn Marino }
1220*e4b17023SJohn Marino
1221*e4b17023SJohn Marino /* Free up the resources allocated to mark_target_live_regs (). This
1222*e4b17023SJohn Marino should be invoked after the last call to mark_target_live_regs (). */
1223*e4b17023SJohn Marino
1224*e4b17023SJohn Marino void
free_resource_info(void)1225*e4b17023SJohn Marino free_resource_info (void)
1226*e4b17023SJohn Marino {
1227*e4b17023SJohn Marino basic_block bb;
1228*e4b17023SJohn Marino
1229*e4b17023SJohn Marino if (target_hash_table != NULL)
1230*e4b17023SJohn Marino {
1231*e4b17023SJohn Marino int i;
1232*e4b17023SJohn Marino
1233*e4b17023SJohn Marino for (i = 0; i < TARGET_HASH_PRIME; ++i)
1234*e4b17023SJohn Marino {
1235*e4b17023SJohn Marino struct target_info *ti = target_hash_table[i];
1236*e4b17023SJohn Marino
1237*e4b17023SJohn Marino while (ti)
1238*e4b17023SJohn Marino {
1239*e4b17023SJohn Marino struct target_info *next = ti->next;
1240*e4b17023SJohn Marino free (ti);
1241*e4b17023SJohn Marino ti = next;
1242*e4b17023SJohn Marino }
1243*e4b17023SJohn Marino }
1244*e4b17023SJohn Marino
1245*e4b17023SJohn Marino free (target_hash_table);
1246*e4b17023SJohn Marino target_hash_table = NULL;
1247*e4b17023SJohn Marino }
1248*e4b17023SJohn Marino
1249*e4b17023SJohn Marino if (bb_ticks != NULL)
1250*e4b17023SJohn Marino {
1251*e4b17023SJohn Marino free (bb_ticks);
1252*e4b17023SJohn Marino bb_ticks = NULL;
1253*e4b17023SJohn Marino }
1254*e4b17023SJohn Marino
1255*e4b17023SJohn Marino FOR_EACH_BB (bb)
1256*e4b17023SJohn Marino if (LABEL_P (BB_HEAD (bb)))
1257*e4b17023SJohn Marino BLOCK_FOR_INSN (BB_HEAD (bb)) = NULL;
1258*e4b17023SJohn Marino }
1259*e4b17023SJohn Marino
1260*e4b17023SJohn Marino /* Clear any hashed information that we have stored for INSN. */
1261*e4b17023SJohn Marino
1262*e4b17023SJohn Marino void
clear_hashed_info_for_insn(rtx insn)1263*e4b17023SJohn Marino clear_hashed_info_for_insn (rtx insn)
1264*e4b17023SJohn Marino {
1265*e4b17023SJohn Marino struct target_info *tinfo;
1266*e4b17023SJohn Marino
1267*e4b17023SJohn Marino if (target_hash_table != NULL)
1268*e4b17023SJohn Marino {
1269*e4b17023SJohn Marino for (tinfo = target_hash_table[INSN_UID (insn) % TARGET_HASH_PRIME];
1270*e4b17023SJohn Marino tinfo; tinfo = tinfo->next)
1271*e4b17023SJohn Marino if (tinfo->uid == INSN_UID (insn))
1272*e4b17023SJohn Marino break;
1273*e4b17023SJohn Marino
1274*e4b17023SJohn Marino if (tinfo)
1275*e4b17023SJohn Marino tinfo->block = -1;
1276*e4b17023SJohn Marino }
1277*e4b17023SJohn Marino }
1278*e4b17023SJohn Marino
1279*e4b17023SJohn Marino /* Increment the tick count for the basic block that contains INSN. */
1280*e4b17023SJohn Marino
1281*e4b17023SJohn Marino void
incr_ticks_for_insn(rtx insn)1282*e4b17023SJohn Marino incr_ticks_for_insn (rtx insn)
1283*e4b17023SJohn Marino {
1284*e4b17023SJohn Marino int b = find_basic_block (insn, MAX_DELAY_SLOT_LIVE_SEARCH);
1285*e4b17023SJohn Marino
1286*e4b17023SJohn Marino if (b != -1)
1287*e4b17023SJohn Marino bb_ticks[b]++;
1288*e4b17023SJohn Marino }
1289*e4b17023SJohn Marino
1290*e4b17023SJohn Marino /* Add TRIAL to the set of resources used at the end of the current
1291*e4b17023SJohn Marino function. */
1292*e4b17023SJohn Marino void
mark_end_of_function_resources(rtx trial,bool include_delayed_effects)1293*e4b17023SJohn Marino mark_end_of_function_resources (rtx trial, bool include_delayed_effects)
1294*e4b17023SJohn Marino {
1295*e4b17023SJohn Marino mark_referenced_resources (trial, &end_of_function_needs,
1296*e4b17023SJohn Marino include_delayed_effects);
1297*e4b17023SJohn Marino }
1298