lra-eliminations.cc revision 1.1 1 /* Code for RTL register eliminations.
2 Copyright (C) 2010-2022 Free Software Foundation, Inc.
3 Contributed by Vladimir Makarov <vmakarov (at) redhat.com>.
4
5 This file is part of GCC.
6
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 3, or (at your option) any later
10 version.
11
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
20
21 /* Eliminable registers (like a soft argument or frame pointer) are
22 widely used in RTL. These eliminable registers should be replaced
23 by real hard registers (like the stack pointer or hard frame
24 pointer) plus some offset. The offsets usually change whenever the
25 stack is expanded. We know the final offsets only at the very end
26 of LRA.
27
28 Within LRA, we usually keep the RTL in such a state that the
29 eliminable registers can be replaced by just the corresponding hard
30 register (without any offset). To achieve this we should add the
31 initial elimination offset at the beginning of LRA and update the
32 offsets whenever the stack is expanded. We need to do this before
33 every constraint pass because the choice of offset often affects
34 whether a particular address or memory constraint is satisfied.
35
36 We keep RTL code at most time in such state that the virtual
37 registers can be changed by just the corresponding hard registers
38 (with zero offsets) and we have the right RTL code. To achieve this
39 we should add initial offset at the beginning of LRA work and update
40 offsets after each stack expanding. But actually we update virtual
41 registers to the same virtual registers + corresponding offsets
42 before every constraint pass because it affects constraint
43 satisfaction (e.g. an address displacement became too big for some
44 target).
45
46 The final change of eliminable registers to the corresponding hard
47 registers are done at the very end of LRA when there were no change
48 in offsets anymore:
49
50 fp + 42 => sp + 42
51
52 */
53
54 #include "config.h"
55 #include "system.h"
56 #include "coretypes.h"
57 #include "backend.h"
58 #include "target.h"
59 #include "rtl.h"
60 #include "tree.h"
61 #include "df.h"
62 #include "memmodel.h"
63 #include "tm_p.h"
64 #include "optabs.h"
65 #include "regs.h"
66 #include "ira.h"
67 #include "recog.h"
68 #include "output.h"
69 #include "rtl-error.h"
70 #include "lra-int.h"
71
72 /* This structure is used to record information about hard register
73 eliminations. */
74 class lra_elim_table
75 {
76 public:
77 /* Hard register number to be eliminated. */
78 int from;
79 /* Hard register number used as replacement. */
80 int to;
81 /* Difference between values of the two hard registers above on
82 previous iteration. */
83 poly_int64 previous_offset;
84 /* Difference between the values on the current iteration. */
85 poly_int64 offset;
86 /* Nonzero if this elimination can be done. */
87 bool can_eliminate;
88 /* CAN_ELIMINATE since the last check. */
89 bool prev_can_eliminate;
90 /* REG rtx for the register to be eliminated. We cannot simply
91 compare the number since we might then spuriously replace a hard
92 register corresponding to a pseudo assigned to the reg to be
93 eliminated. */
94 rtx from_rtx;
95 /* REG rtx for the replacement. */
96 rtx to_rtx;
97 };
98
99 /* The elimination table. Each array entry describes one possible way
100 of eliminating a register in favor of another. If there is more
101 than one way of eliminating a particular register, the most
102 preferred should be specified first. */
103 static class lra_elim_table *reg_eliminate = 0;
104
105 /* This is an intermediate structure to initialize the table. It has
106 exactly the members provided by ELIMINABLE_REGS. */
107 static const struct elim_table_1
108 {
109 const int from;
110 const int to;
111 } reg_eliminate_1[] =
112
113 ELIMINABLE_REGS;
114
115 #define NUM_ELIMINABLE_REGS ARRAY_SIZE (reg_eliminate_1)
116
117 /* Print info about elimination table to file F. */
118 static void
119 print_elim_table (FILE *f)
120 {
121 class lra_elim_table *ep;
122
123 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
124 {
125 fprintf (f, "%s eliminate %d to %d (offset=",
126 ep->can_eliminate ? "Can" : "Can't", ep->from, ep->to);
127 print_dec (ep->offset, f);
128 fprintf (f, ", prev_offset=");
129 print_dec (ep->previous_offset, f);
130 fprintf (f, ")\n");
131 }
132 }
133
134 /* Print info about elimination table to stderr. */
135 void
136 lra_debug_elim_table (void)
137 {
138 print_elim_table (stderr);
139 }
140
141 /* Setup possibility of elimination in elimination table element EP to
142 VALUE. Setup FRAME_POINTER_NEEDED if elimination from frame
143 pointer to stack pointer is not possible anymore. */
144 static void
145 setup_can_eliminate (class lra_elim_table *ep, bool value)
146 {
147 ep->can_eliminate = ep->prev_can_eliminate = value;
148 if (! value
149 && ep->from == FRAME_POINTER_REGNUM && ep->to == STACK_POINTER_REGNUM)
150 frame_pointer_needed = 1;
151 if (!frame_pointer_needed)
152 REGNO_POINTER_ALIGN (HARD_FRAME_POINTER_REGNUM) = 0;
153 }
154
155 /* Map: eliminable "from" register -> its current elimination,
156 or NULL if none. The elimination table may contain more than
157 one elimination for the same hard register, but this map specifies
158 the one that we are currently using. */
159 static class lra_elim_table *elimination_map[FIRST_PSEUDO_REGISTER];
160
161 /* When an eliminable hard register becomes not eliminable, we use the
162 following special structure to restore original offsets for the
163 register. */
164 static class lra_elim_table self_elim_table;
165
166 /* Offsets should be used to restore original offsets for eliminable
167 hard register which just became not eliminable. Zero,
168 otherwise. */
169 static poly_int64_pod self_elim_offsets[FIRST_PSEUDO_REGISTER];
170
171 /* Map: hard regno -> RTL presentation. RTL presentations of all
172 potentially eliminable hard registers are stored in the map. */
173 static rtx eliminable_reg_rtx[FIRST_PSEUDO_REGISTER];
174
175 /* Set up ELIMINATION_MAP of the currently used eliminations. */
176 static void
177 setup_elimination_map (void)
178 {
179 int i;
180 class lra_elim_table *ep;
181
182 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
183 elimination_map[i] = NULL;
184 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
185 if (ep->can_eliminate && elimination_map[ep->from] == NULL)
186 elimination_map[ep->from] = ep;
187 }
188
189
190
192 /* Compute the sum of X and Y, making canonicalizations assumed in an
193 address, namely: sum constant integers, surround the sum of two
194 constants with a CONST, put the constant as the second operand, and
195 group the constant on the outermost sum.
196
197 This routine assumes both inputs are already in canonical form. */
198 static rtx
199 form_sum (rtx x, rtx y)
200 {
201 machine_mode mode = GET_MODE (x);
202 poly_int64 offset;
203
204 if (mode == VOIDmode)
205 mode = GET_MODE (y);
206
207 if (mode == VOIDmode)
208 mode = Pmode;
209
210 if (poly_int_rtx_p (x, &offset))
211 return plus_constant (mode, y, offset);
212 else if (poly_int_rtx_p (y, &offset))
213 return plus_constant (mode, x, offset);
214 else if (CONSTANT_P (x))
215 std::swap (x, y);
216
217 if (GET_CODE (x) == PLUS && CONSTANT_P (XEXP (x, 1)))
218 return form_sum (XEXP (x, 0), form_sum (XEXP (x, 1), y));
219
220 /* Note that if the operands of Y are specified in the opposite
221 order in the recursive calls below, infinite recursion will
222 occur. */
223 if (GET_CODE (y) == PLUS && CONSTANT_P (XEXP (y, 1)))
224 return form_sum (form_sum (x, XEXP (y, 0)), XEXP (y, 1));
225
226 /* If both constant, encapsulate sum. Otherwise, just form sum. A
227 constant will have been placed second. */
228 if (CONSTANT_P (x) && CONSTANT_P (y))
229 {
230 if (GET_CODE (x) == CONST)
231 x = XEXP (x, 0);
232 if (GET_CODE (y) == CONST)
233 y = XEXP (y, 0);
234
235 return gen_rtx_CONST (VOIDmode, gen_rtx_PLUS (mode, x, y));
236 }
237
238 return gen_rtx_PLUS (mode, x, y);
239 }
240
241 /* Return the current substitution hard register of the elimination of
242 HARD_REGNO. If HARD_REGNO is not eliminable, return itself. */
243 int
244 lra_get_elimination_hard_regno (int hard_regno)
245 {
246 class lra_elim_table *ep;
247
248 if (hard_regno < 0 || hard_regno >= FIRST_PSEUDO_REGISTER)
249 return hard_regno;
250 if ((ep = elimination_map[hard_regno]) == NULL)
251 return hard_regno;
252 return ep->to;
253 }
254
255 /* Return elimination which will be used for hard reg REG, NULL
256 otherwise. */
257 static class lra_elim_table *
258 get_elimination (rtx reg)
259 {
260 int hard_regno;
261 class lra_elim_table *ep;
262
263 lra_assert (REG_P (reg));
264 if ((hard_regno = REGNO (reg)) < 0 || hard_regno >= FIRST_PSEUDO_REGISTER)
265 return NULL;
266 if ((ep = elimination_map[hard_regno]) != NULL)
267 return ep->from_rtx != reg ? NULL : ep;
268 poly_int64 offset = self_elim_offsets[hard_regno];
269 if (known_eq (offset, 0))
270 return NULL;
271 /* This is an iteration to restore offsets just after HARD_REGNO
272 stopped to be eliminable. */
273 self_elim_table.from = self_elim_table.to = hard_regno;
274 self_elim_table.from_rtx
275 = self_elim_table.to_rtx
276 = eliminable_reg_rtx[hard_regno];
277 lra_assert (self_elim_table.from_rtx != NULL);
278 self_elim_table.offset = offset;
279 return &self_elim_table;
280 }
281
282 /* Transform (subreg (plus reg const)) to (plus (subreg reg) const)
283 when it is possible. Return X or the transformation result if the
284 transformation is done. */
285 static rtx
286 move_plus_up (rtx x)
287 {
288 rtx subreg_reg;
289 machine_mode x_mode, subreg_reg_mode;
290
291 if (GET_CODE (x) != SUBREG || !subreg_lowpart_p (x))
292 return x;
293 subreg_reg = SUBREG_REG (x);
294 x_mode = GET_MODE (x);
295 subreg_reg_mode = GET_MODE (subreg_reg);
296 if (!paradoxical_subreg_p (x)
297 && GET_CODE (subreg_reg) == PLUS
298 && CONSTANT_P (XEXP (subreg_reg, 1))
299 && GET_MODE_CLASS (x_mode) == MODE_INT
300 && GET_MODE_CLASS (subreg_reg_mode) == MODE_INT)
301 {
302 rtx cst = simplify_subreg (x_mode, XEXP (subreg_reg, 1), subreg_reg_mode,
303 subreg_lowpart_offset (x_mode,
304 subreg_reg_mode));
305 if (cst && CONSTANT_P (cst))
306 return gen_rtx_PLUS (x_mode, lowpart_subreg (x_mode,
307 XEXP (subreg_reg, 0),
308 subreg_reg_mode), cst);
309 }
310 return x;
311 }
312
313 /* Scan X and replace any eliminable registers (such as fp) with a
314 replacement (such as sp) if SUBST_P, plus an offset. The offset is
315 a change in the offset between the eliminable register and its
316 substitution if UPDATE_P, or the full offset if FULL_P, or
317 otherwise zero. If FULL_P, we also use the SP offsets for
318 elimination to SP. If UPDATE_P, use UPDATE_SP_OFFSET for updating
319 offsets of register elimnable to SP. If UPDATE_SP_OFFSET is
320 non-zero, don't use difference of the offset and the previous
321 offset.
322
323 MEM_MODE is the mode of an enclosing MEM. We need this to know how
324 much to adjust a register for, e.g., PRE_DEC. Also, if we are
325 inside a MEM, we are allowed to replace a sum of a hard register
326 and the constant zero with the hard register, which we cannot do
327 outside a MEM. In addition, we need to record the fact that a
328 hard register is referenced outside a MEM.
329
330 If we make full substitution to SP for non-null INSN, add the insn
331 sp offset. */
332 rtx
333 lra_eliminate_regs_1 (rtx_insn *insn, rtx x, machine_mode mem_mode,
334 bool subst_p, bool update_p,
335 poly_int64 update_sp_offset, bool full_p)
336 {
337 enum rtx_code code = GET_CODE (x);
338 class lra_elim_table *ep;
339 rtx new_rtx;
340 int i, j;
341 const char *fmt;
342 int copied = 0;
343
344 lra_assert (!update_p || !full_p);
345 lra_assert (known_eq (update_sp_offset, 0)
346 || (!subst_p && update_p && !full_p));
347 if (! current_function_decl)
348 return x;
349
350 switch (code)
351 {
352 CASE_CONST_ANY:
353 case CONST:
354 case SYMBOL_REF:
355 case CODE_LABEL:
356 case PC:
357 case ASM_INPUT:
358 case ADDR_VEC:
359 case ADDR_DIFF_VEC:
360 case RETURN:
361 return x;
362
363 case REG:
364 /* First handle the case where we encounter a bare hard register
365 that is eliminable. Replace it with a PLUS. */
366 if ((ep = get_elimination (x)) != NULL)
367 {
368 rtx to = subst_p ? ep->to_rtx : ep->from_rtx;
369
370 if (maybe_ne (update_sp_offset, 0))
371 {
372 if (ep->to_rtx == stack_pointer_rtx)
373 return plus_constant (Pmode, to, update_sp_offset);
374 return to;
375 }
376 else if (update_p)
377 return plus_constant (Pmode, to, ep->offset - ep->previous_offset);
378 else if (full_p)
379 return plus_constant (Pmode, to,
380 ep->offset
381 - (insn != NULL_RTX
382 && ep->to_rtx == stack_pointer_rtx
383 ? lra_get_insn_recog_data (insn)->sp_offset
384 : 0));
385 else
386 return to;
387 }
388 return x;
389
390 case PLUS:
391 /* If this is the sum of an eliminable register and a constant, rework
392 the sum. */
393 if (REG_P (XEXP (x, 0)) && CONSTANT_P (XEXP (x, 1)))
394 {
395 if ((ep = get_elimination (XEXP (x, 0))) != NULL)
396 {
397 poly_int64 offset, curr_offset;
398 rtx to = subst_p ? ep->to_rtx : ep->from_rtx;
399
400 if (! update_p && ! full_p)
401 return simplify_gen_binary (PLUS, Pmode, to, XEXP (x, 1));
402
403 if (maybe_ne (update_sp_offset, 0))
404 offset = ep->to_rtx == stack_pointer_rtx ? update_sp_offset : 0;
405 else
406 offset = (update_p
407 ? ep->offset - ep->previous_offset : ep->offset);
408 if (full_p && insn != NULL_RTX && ep->to_rtx == stack_pointer_rtx)
409 offset -= lra_get_insn_recog_data (insn)->sp_offset;
410 if (poly_int_rtx_p (XEXP (x, 1), &curr_offset)
411 && known_eq (curr_offset, -offset))
412 return to;
413 else
414 return gen_rtx_PLUS (Pmode, to,
415 plus_constant (Pmode,
416 XEXP (x, 1), offset));
417 }
418
419 /* If the hard register is not eliminable, we are done since
420 the other operand is a constant. */
421 return x;
422 }
423
424 /* If this is part of an address, we want to bring any constant
425 to the outermost PLUS. We will do this by doing hard
426 register replacement in our operands and seeing if a constant
427 shows up in one of them.
428
429 Note that there is no risk of modifying the structure of the
430 insn, since we only get called for its operands, thus we are
431 either modifying the address inside a MEM, or something like
432 an address operand of a load-address insn. */
433
434 {
435 rtx new0 = lra_eliminate_regs_1 (insn, XEXP (x, 0), mem_mode,
436 subst_p, update_p,
437 update_sp_offset, full_p);
438 rtx new1 = lra_eliminate_regs_1 (insn, XEXP (x, 1), mem_mode,
439 subst_p, update_p,
440 update_sp_offset, full_p);
441
442 new0 = move_plus_up (new0);
443 new1 = move_plus_up (new1);
444 if (new0 != XEXP (x, 0) || new1 != XEXP (x, 1))
445 return form_sum (new0, new1);
446 }
447 return x;
448
449 case MULT:
450 /* If this is the product of an eliminable hard register and a
451 constant, apply the distribute law and move the constant out
452 so that we have (plus (mult ..) ..). This is needed in order
453 to keep load-address insns valid. This case is pathological.
454 We ignore the possibility of overflow here. */
455 if (REG_P (XEXP (x, 0)) && CONST_INT_P (XEXP (x, 1))
456 && (ep = get_elimination (XEXP (x, 0))) != NULL)
457 {
458 rtx to = subst_p ? ep->to_rtx : ep->from_rtx;
459
460 if (maybe_ne (update_sp_offset, 0))
461 {
462 if (ep->to_rtx == stack_pointer_rtx)
463 return plus_constant (Pmode,
464 gen_rtx_MULT (Pmode, to, XEXP (x, 1)),
465 update_sp_offset * INTVAL (XEXP (x, 1)));
466 return gen_rtx_MULT (Pmode, to, XEXP (x, 1));
467 }
468 else if (update_p)
469 return plus_constant (Pmode,
470 gen_rtx_MULT (Pmode, to, XEXP (x, 1)),
471 (ep->offset - ep->previous_offset)
472 * INTVAL (XEXP (x, 1)));
473 else if (full_p)
474 {
475 poly_int64 offset = ep->offset;
476
477 if (insn != NULL_RTX && ep->to_rtx == stack_pointer_rtx)
478 offset -= lra_get_insn_recog_data (insn)->sp_offset;
479 return
480 plus_constant (Pmode,
481 gen_rtx_MULT (Pmode, to, XEXP (x, 1)),
482 offset * INTVAL (XEXP (x, 1)));
483 }
484 else
485 return gen_rtx_MULT (Pmode, to, XEXP (x, 1));
486 }
487
488 /* fall through */
489
490 case CALL:
491 case COMPARE:
492 /* See comments before PLUS about handling MINUS. */
493 case MINUS:
494 case DIV: case UDIV:
495 case MOD: case UMOD:
496 case AND: case IOR: case XOR:
497 case ROTATERT: case ROTATE:
498 case ASHIFTRT: case LSHIFTRT: case ASHIFT:
499 case NE: case EQ:
500 case GE: case GT: case GEU: case GTU:
501 case LE: case LT: case LEU: case LTU:
502 {
503 rtx new0 = lra_eliminate_regs_1 (insn, XEXP (x, 0), mem_mode,
504 subst_p, update_p,
505 update_sp_offset, full_p);
506 rtx new1 = XEXP (x, 1)
507 ? lra_eliminate_regs_1 (insn, XEXP (x, 1), mem_mode,
508 subst_p, update_p,
509 update_sp_offset, full_p) : 0;
510
511 if (new0 != XEXP (x, 0) || new1 != XEXP (x, 1))
512 return gen_rtx_fmt_ee (code, GET_MODE (x), new0, new1);
513 }
514 return x;
515
516 case EXPR_LIST:
517 /* If we have something in XEXP (x, 0), the usual case,
518 eliminate it. */
519 if (XEXP (x, 0))
520 {
521 new_rtx = lra_eliminate_regs_1 (insn, XEXP (x, 0), mem_mode,
522 subst_p, update_p,
523 update_sp_offset, full_p);
524 if (new_rtx != XEXP (x, 0))
525 {
526 /* If this is a REG_DEAD note, it is not valid anymore.
527 Using the eliminated version could result in creating a
528 REG_DEAD note for the stack or frame pointer. */
529 if (REG_NOTE_KIND (x) == REG_DEAD)
530 return (XEXP (x, 1)
531 ? lra_eliminate_regs_1 (insn, XEXP (x, 1), mem_mode,
532 subst_p, update_p,
533 update_sp_offset, full_p)
534 : NULL_RTX);
535
536 x = alloc_reg_note (REG_NOTE_KIND (x), new_rtx, XEXP (x, 1));
537 }
538 }
539
540 /* fall through */
541
542 case INSN_LIST:
543 case INT_LIST:
544 /* Now do eliminations in the rest of the chain. If this was
545 an EXPR_LIST, this might result in allocating more memory than is
546 strictly needed, but it simplifies the code. */
547 if (XEXP (x, 1))
548 {
549 new_rtx = lra_eliminate_regs_1 (insn, XEXP (x, 1), mem_mode,
550 subst_p, update_p,
551 update_sp_offset, full_p);
552 if (new_rtx != XEXP (x, 1))
553 return
554 gen_rtx_fmt_ee (GET_CODE (x), GET_MODE (x),
555 XEXP (x, 0), new_rtx);
556 }
557 return x;
558
559 case PRE_INC:
560 case POST_INC:
561 case PRE_DEC:
562 case POST_DEC:
563 /* We do not support elimination of a register that is modified.
564 elimination_effects has already make sure that this does not
565 happen. */
566 return x;
567
568 case PRE_MODIFY:
569 case POST_MODIFY:
570 /* We do not support elimination of a hard register that is
571 modified. LRA has already make sure that this does not
572 happen. The only remaining case we need to consider here is
573 that the increment value may be an eliminable register. */
574 if (GET_CODE (XEXP (x, 1)) == PLUS
575 && XEXP (XEXP (x, 1), 0) == XEXP (x, 0))
576 {
577 rtx new_rtx = lra_eliminate_regs_1 (insn, XEXP (XEXP (x, 1), 1),
578 mem_mode, subst_p, update_p,
579 update_sp_offset, full_p);
580
581 if (new_rtx != XEXP (XEXP (x, 1), 1))
582 return gen_rtx_fmt_ee (code, GET_MODE (x), XEXP (x, 0),
583 gen_rtx_PLUS (GET_MODE (x),
584 XEXP (x, 0), new_rtx));
585 }
586 return x;
587
588 case STRICT_LOW_PART:
589 case NEG: case NOT:
590 case SIGN_EXTEND: case ZERO_EXTEND:
591 case TRUNCATE: case FLOAT_EXTEND: case FLOAT_TRUNCATE:
592 case FLOAT: case FIX:
593 case UNSIGNED_FIX: case UNSIGNED_FLOAT:
594 case ABS:
595 case SQRT:
596 case FFS:
597 case CLZ:
598 case CTZ:
599 case POPCOUNT:
600 case PARITY:
601 case BSWAP:
602 new_rtx = lra_eliminate_regs_1 (insn, XEXP (x, 0), mem_mode,
603 subst_p, update_p,
604 update_sp_offset, full_p);
605 if (new_rtx != XEXP (x, 0))
606 return gen_rtx_fmt_e (code, GET_MODE (x), new_rtx);
607 return x;
608
609 case SUBREG:
610 new_rtx = lra_eliminate_regs_1 (insn, SUBREG_REG (x), mem_mode,
611 subst_p, update_p,
612 update_sp_offset, full_p);
613
614 if (new_rtx != SUBREG_REG (x))
615 {
616 if (MEM_P (new_rtx) && !paradoxical_subreg_p (x))
617 {
618 SUBREG_REG (x) = new_rtx;
619 alter_subreg (&x, false);
620 return x;
621 }
622 else if (! subst_p)
623 {
624 /* LRA can transform subregs itself. So don't call
625 simplify_gen_subreg until LRA transformations are
626 finished. Function simplify_gen_subreg can do
627 non-trivial transformations (like truncation) which
628 might make LRA work to fail. */
629 SUBREG_REG (x) = new_rtx;
630 return x;
631 }
632 else
633 return simplify_gen_subreg (GET_MODE (x), new_rtx,
634 GET_MODE (new_rtx), SUBREG_BYTE (x));
635 }
636
637 return x;
638
639 case MEM:
640 /* Our only special processing is to pass the mode of the MEM to our
641 recursive call and copy the flags. While we are here, handle this
642 case more efficiently. */
643 return
644 replace_equiv_address_nv
645 (x,
646 lra_eliminate_regs_1 (insn, XEXP (x, 0), GET_MODE (x),
647 subst_p, update_p, update_sp_offset, full_p));
648
649 case USE:
650 /* Handle insn_list USE that a call to a pure function may generate. */
651 new_rtx = lra_eliminate_regs_1 (insn, XEXP (x, 0), VOIDmode,
652 subst_p, update_p, update_sp_offset, full_p);
653 if (new_rtx != XEXP (x, 0))
654 return gen_rtx_USE (GET_MODE (x), new_rtx);
655 return x;
656
657 case CLOBBER:
658 case SET:
659 gcc_unreachable ();
660
661 default:
662 break;
663 }
664
665 /* Process each of our operands recursively. If any have changed, make a
666 copy of the rtx. */
667 fmt = GET_RTX_FORMAT (code);
668 for (i = 0; i < GET_RTX_LENGTH (code); i++, fmt++)
669 {
670 if (*fmt == 'e')
671 {
672 new_rtx = lra_eliminate_regs_1 (insn, XEXP (x, i), mem_mode,
673 subst_p, update_p,
674 update_sp_offset, full_p);
675 if (new_rtx != XEXP (x, i) && ! copied)
676 {
677 x = shallow_copy_rtx (x);
678 copied = 1;
679 }
680 XEXP (x, i) = new_rtx;
681 }
682 else if (*fmt == 'E')
683 {
684 int copied_vec = 0;
685 for (j = 0; j < XVECLEN (x, i); j++)
686 {
687 new_rtx = lra_eliminate_regs_1 (insn, XVECEXP (x, i, j), mem_mode,
688 subst_p, update_p,
689 update_sp_offset, full_p);
690 if (new_rtx != XVECEXP (x, i, j) && ! copied_vec)
691 {
692 rtvec new_v = gen_rtvec_v (XVECLEN (x, i),
693 XVEC (x, i)->elem);
694 if (! copied)
695 {
696 x = shallow_copy_rtx (x);
697 copied = 1;
698 }
699 XVEC (x, i) = new_v;
700 copied_vec = 1;
701 }
702 XVECEXP (x, i, j) = new_rtx;
703 }
704 }
705 }
706
707 return x;
708 }
709
710 /* This function is used externally in subsequent passes of GCC. It
711 always does a full elimination of X. */
712 rtx
713 lra_eliminate_regs (rtx x, machine_mode mem_mode,
714 rtx insn ATTRIBUTE_UNUSED)
715 {
716 return lra_eliminate_regs_1 (NULL, x, mem_mode, true, false, 0, true);
717 }
718
719 /* Stack pointer offset before the current insn relative to one at the
720 func start. RTL insns can change SP explicitly. We keep the
721 changes from one insn to another through this variable. */
722 static poly_int64 curr_sp_change;
723
724 /* Scan rtx X for references to elimination source or target registers
725 in contexts that would prevent the elimination from happening.
726 Update the table of eliminables to reflect the changed state.
727 MEM_MODE is the mode of an enclosing MEM rtx, or VOIDmode if not
728 within a MEM. */
729 static void
730 mark_not_eliminable (rtx x, machine_mode mem_mode)
731 {
732 enum rtx_code code = GET_CODE (x);
733 class lra_elim_table *ep;
734 int i, j;
735 const char *fmt;
736 poly_int64 offset = 0;
737
738 switch (code)
739 {
740 case PRE_INC:
741 case POST_INC:
742 case PRE_DEC:
743 case POST_DEC:
744 case POST_MODIFY:
745 case PRE_MODIFY:
746 if (XEXP (x, 0) == stack_pointer_rtx
747 && ((code != PRE_MODIFY && code != POST_MODIFY)
748 || (GET_CODE (XEXP (x, 1)) == PLUS
749 && XEXP (x, 0) == XEXP (XEXP (x, 1), 0)
750 && poly_int_rtx_p (XEXP (XEXP (x, 1), 1), &offset))))
751 {
752 poly_int64 size = GET_MODE_SIZE (mem_mode);
753
754 #ifdef PUSH_ROUNDING
755 /* If more bytes than MEM_MODE are pushed, account for
756 them. */
757 size = PUSH_ROUNDING (size);
758 #endif
759 if (code == PRE_DEC || code == POST_DEC)
760 curr_sp_change -= size;
761 else if (code == PRE_INC || code == POST_INC)
762 curr_sp_change += size;
763 else if (code == PRE_MODIFY || code == POST_MODIFY)
764 curr_sp_change += offset;
765 }
766 else if (REG_P (XEXP (x, 0))
767 && REGNO (XEXP (x, 0)) >= FIRST_PSEUDO_REGISTER)
768 {
769 /* If we modify the source of an elimination rule, disable
770 it. Do the same if it is the destination and not the
771 hard frame register. */
772 for (ep = reg_eliminate;
773 ep < ®_eliminate[NUM_ELIMINABLE_REGS];
774 ep++)
775 if (ep->from_rtx == XEXP (x, 0)
776 || (ep->to_rtx == XEXP (x, 0)
777 && ep->to_rtx != hard_frame_pointer_rtx))
778 setup_can_eliminate (ep, false);
779 }
780 return;
781
782 case USE:
783 if (REG_P (XEXP (x, 0)) && REGNO (XEXP (x, 0)) < FIRST_PSEUDO_REGISTER)
784 /* If using a hard register that is the source of an eliminate
785 we still think can be performed, note it cannot be
786 performed since we don't know how this hard register is
787 used. */
788 for (ep = reg_eliminate;
789 ep < ®_eliminate[NUM_ELIMINABLE_REGS];
790 ep++)
791 if (ep->from_rtx == XEXP (x, 0)
792 && ep->to_rtx != hard_frame_pointer_rtx)
793 setup_can_eliminate (ep, false);
794 return;
795
796 case CLOBBER:
797 if (REG_P (XEXP (x, 0)) && REGNO (XEXP (x, 0)) < FIRST_PSEUDO_REGISTER)
798 /* If clobbering a hard register that is the replacement
799 register for an elimination we still think can be
800 performed, note that it cannot be performed. Otherwise, we
801 need not be concerned about it. */
802 for (ep = reg_eliminate;
803 ep < ®_eliminate[NUM_ELIMINABLE_REGS];
804 ep++)
805 if (ep->to_rtx == XEXP (x, 0)
806 && ep->to_rtx != hard_frame_pointer_rtx)
807 setup_can_eliminate (ep, false);
808 return;
809
810 case SET:
811 if (SET_DEST (x) == stack_pointer_rtx
812 && GET_CODE (SET_SRC (x)) == PLUS
813 && XEXP (SET_SRC (x), 0) == SET_DEST (x)
814 && poly_int_rtx_p (XEXP (SET_SRC (x), 1), &offset))
815 {
816 curr_sp_change += offset;
817 return;
818 }
819 if (! REG_P (SET_DEST (x))
820 || REGNO (SET_DEST (x)) >= FIRST_PSEUDO_REGISTER)
821 mark_not_eliminable (SET_DEST (x), mem_mode);
822 else
823 {
824 /* See if this is setting the replacement hard register for
825 an elimination.
826
827 If DEST is the hard frame pointer, we do nothing because
828 we assume that all assignments to the frame pointer are
829 for non-local gotos and are being done at a time when
830 they are valid and do not disturb anything else. Some
831 machines want to eliminate a fake argument pointer (or
832 even a fake frame pointer) with either the real frame
833 pointer or the stack pointer. Assignments to the hard
834 frame pointer must not prevent this elimination. */
835 for (ep = reg_eliminate;
836 ep < ®_eliminate[NUM_ELIMINABLE_REGS];
837 ep++)
838 if (ep->to_rtx == SET_DEST (x)
839 && SET_DEST (x) != hard_frame_pointer_rtx)
840 setup_can_eliminate (ep, false);
841 }
842
843 mark_not_eliminable (SET_SRC (x), mem_mode);
844 return;
845
846 case MEM:
847 /* Our only special processing is to pass the mode of the MEM to
848 our recursive call. */
849 mark_not_eliminable (XEXP (x, 0), GET_MODE (x));
850 return;
851
852 default:
853 break;
854 }
855
856 fmt = GET_RTX_FORMAT (code);
857 for (i = 0; i < GET_RTX_LENGTH (code); i++, fmt++)
858 {
859 if (*fmt == 'e')
860 mark_not_eliminable (XEXP (x, i), mem_mode);
861 else if (*fmt == 'E')
862 for (j = 0; j < XVECLEN (x, i); j++)
863 mark_not_eliminable (XVECEXP (x, i, j), mem_mode);
864 }
865 }
866
867
868
870 /* Scan INSN and eliminate all eliminable hard registers in it.
871
872 If REPLACE_P is true, do the replacement destructively. Also
873 delete the insn as dead it if it is setting an eliminable register.
874
875 If REPLACE_P is false, just update the offsets while keeping the
876 base register the same. If FIRST_P, use the sp offset for
877 elimination to sp. Otherwise, use UPDATE_SP_OFFSET for this. If
878 UPDATE_SP_OFFSET is non-zero, don't use difference of the offset
879 and the previous offset. Attach the note about used elimination
880 for insns setting frame pointer to update elimination easy (without
881 parsing already generated elimination insns to find offset
882 previously used) in future. */
883
884 void
885 eliminate_regs_in_insn (rtx_insn *insn, bool replace_p, bool first_p,
886 poly_int64 update_sp_offset)
887 {
888 int icode = recog_memoized (insn);
889 rtx set, old_set = single_set (insn);
890 bool validate_p;
891 int i;
892 rtx substed_operand[MAX_RECOG_OPERANDS];
893 rtx orig_operand[MAX_RECOG_OPERANDS];
894 class lra_elim_table *ep;
895 rtx plus_src, plus_cst_src;
896 lra_insn_recog_data_t id;
897 struct lra_static_insn_data *static_id;
898
899 if (icode < 0 && asm_noperands (PATTERN (insn)) < 0 && ! DEBUG_INSN_P (insn))
900 {
901 lra_assert (GET_CODE (PATTERN (insn)) == USE
902 || GET_CODE (PATTERN (insn)) == CLOBBER
903 || GET_CODE (PATTERN (insn)) == ASM_INPUT);
904 return;
905 }
906
907 /* We allow one special case which happens to work on all machines we
908 currently support: a single set with the source or a REG_EQUAL
909 note being a PLUS of an eliminable register and a constant. */
910 plus_src = plus_cst_src = 0;
911 poly_int64 offset = 0;
912 if (old_set && REG_P (SET_DEST (old_set)))
913 {
914 if (GET_CODE (SET_SRC (old_set)) == PLUS)
915 plus_src = SET_SRC (old_set);
916 /* First see if the source is of the form (plus (...) CST). */
917 if (plus_src && poly_int_rtx_p (XEXP (plus_src, 1), &offset))
918 plus_cst_src = plus_src;
919 /* Check that the first operand of the PLUS is a hard reg or
920 the lowpart subreg of one. */
921 if (plus_cst_src)
922 {
923 rtx reg = XEXP (plus_cst_src, 0);
924
925 if (GET_CODE (reg) == SUBREG && subreg_lowpart_p (reg))
926 reg = SUBREG_REG (reg);
927
928 if (!REG_P (reg) || REGNO (reg) >= FIRST_PSEUDO_REGISTER)
929 plus_cst_src = 0;
930 }
931 }
932 if (plus_cst_src)
933 {
934 rtx reg = XEXP (plus_cst_src, 0);
935
936 if (GET_CODE (reg) == SUBREG)
937 reg = SUBREG_REG (reg);
938
939 if (REG_P (reg) && (ep = get_elimination (reg)) != NULL)
940 {
941 rtx to_rtx = replace_p ? ep->to_rtx : ep->from_rtx;
942
943 if (! replace_p)
944 {
945 if (known_eq (update_sp_offset, 0))
946 offset += (ep->offset - ep->previous_offset);
947 if (ep->to_rtx == stack_pointer_rtx)
948 {
949 if (first_p)
950 offset -= lra_get_insn_recog_data (insn)->sp_offset;
951 else
952 offset += update_sp_offset;
953 }
954 offset = trunc_int_for_mode (offset, GET_MODE (plus_cst_src));
955 }
956
957 if (GET_CODE (XEXP (plus_cst_src, 0)) == SUBREG)
958 to_rtx = gen_lowpart (GET_MODE (XEXP (plus_cst_src, 0)), to_rtx);
959 /* If we have a nonzero offset, and the source is already a
960 simple REG, the following transformation would increase
961 the cost of the insn by replacing a simple REG with (plus
962 (reg sp) CST). So try only when we already had a PLUS
963 before. */
964 if (known_eq (offset, 0) || plus_src)
965 {
966 rtx new_src = plus_constant (GET_MODE (to_rtx), to_rtx, offset);
967
968 old_set = single_set (insn);
969
970 /* First see if this insn remains valid when we make the
971 change. If not, try to replace the whole pattern
972 with a simple set (this may help if the original insn
973 was a PARALLEL that was only recognized as single_set
974 due to REG_UNUSED notes). If this isn't valid
975 either, keep the INSN_CODE the same and let the
976 constraint pass fix it up. */
977 if (! validate_change (insn, &SET_SRC (old_set), new_src, 0))
978 {
979 rtx new_pat = gen_rtx_SET (SET_DEST (old_set), new_src);
980
981 if (! validate_change (insn, &PATTERN (insn), new_pat, 0))
982 SET_SRC (old_set) = new_src;
983 }
984 lra_update_insn_recog_data (insn);
985 /* This can't have an effect on elimination offsets, so skip
986 right to the end. */
987 return;
988 }
989 }
990 }
991
992 /* Eliminate all eliminable registers occurring in operands that
993 can be handled by the constraint pass. */
994 id = lra_get_insn_recog_data (insn);
995 static_id = id->insn_static_data;
996 validate_p = false;
997 for (i = 0; i < static_id->n_operands; i++)
998 {
999 orig_operand[i] = *id->operand_loc[i];
1000 substed_operand[i] = *id->operand_loc[i];
1001
1002 /* For an asm statement, every operand is eliminable. */
1003 if (icode < 0 || insn_data[icode].operand[i].eliminable)
1004 {
1005 /* Check for setting a hard register that we know about. */
1006 if (static_id->operand[i].type != OP_IN
1007 && REG_P (orig_operand[i]))
1008 {
1009 /* If we are assigning to a hard register that can be
1010 eliminated, it must be as part of a PARALLEL, since
1011 the code above handles single SETs. This reg cannot
1012 be longer eliminated -- it is forced by
1013 mark_not_eliminable. */
1014 for (ep = reg_eliminate;
1015 ep < ®_eliminate[NUM_ELIMINABLE_REGS];
1016 ep++)
1017 lra_assert (ep->from_rtx != orig_operand[i]
1018 || ! ep->can_eliminate);
1019 }
1020
1021 /* Companion to the above plus substitution, we can allow
1022 invariants as the source of a plain move. */
1023 substed_operand[i]
1024 = lra_eliminate_regs_1 (insn, *id->operand_loc[i], VOIDmode,
1025 replace_p, ! replace_p && ! first_p,
1026 update_sp_offset, first_p);
1027 if (substed_operand[i] != orig_operand[i])
1028 validate_p = true;
1029 }
1030 }
1031
1032 if (! validate_p)
1033 return;
1034
1035 /* Substitute the operands; the new values are in the substed_operand
1036 array. */
1037 for (i = 0; i < static_id->n_operands; i++)
1038 *id->operand_loc[i] = substed_operand[i];
1039 for (i = 0; i < static_id->n_dups; i++)
1040 *id->dup_loc[i] = substed_operand[(int) static_id->dup_num[i]];
1041
1042 /* Transform plus (plus (hard reg, const), pseudo) to plus (plus (pseudo,
1043 const), hard reg) in order to keep insn containing eliminated register
1044 after all reloads calculating its offset. This permits to keep register
1045 pressure under control and helps to avoid LRA cycling in patalogical
1046 cases. */
1047 if (! replace_p && (set = single_set (insn)) != NULL
1048 && GET_CODE (SET_SRC (set)) == PLUS
1049 && GET_CODE (XEXP (SET_SRC (set), 0)) == PLUS)
1050 {
1051 rtx reg1, reg2, op1, op2;
1052
1053 reg1 = op1 = XEXP (XEXP (SET_SRC (set), 0), 0);
1054 reg2 = op2 = XEXP (SET_SRC (set), 1);
1055 if (GET_CODE (reg1) == SUBREG)
1056 reg1 = SUBREG_REG (reg1);
1057 if (GET_CODE (reg2) == SUBREG)
1058 reg2 = SUBREG_REG (reg2);
1059 if (REG_P (reg1) && REG_P (reg2)
1060 && REGNO (reg1) < FIRST_PSEUDO_REGISTER
1061 && REGNO (reg2) >= FIRST_PSEUDO_REGISTER
1062 && GET_MODE (reg1) == Pmode
1063 && !have_addptr3_insn (lra_pmode_pseudo, reg1,
1064 XEXP (XEXP (SET_SRC (set), 0), 1)))
1065 {
1066 XEXP (XEXP (SET_SRC (set), 0), 0) = op2;
1067 XEXP (SET_SRC (set), 1) = op1;
1068 }
1069 }
1070
1071 /* If we had a move insn but now we don't, re-recognize it.
1072 This will cause spurious re-recognition if the old move had a
1073 PARALLEL since the new one still will, but we can't call
1074 single_set without having put new body into the insn and the
1075 re-recognition won't hurt in this rare case. */
1076 lra_update_insn_recog_data (insn);
1077 }
1078
1079 /* Spill pseudos which are assigned to hard registers in SET. Add
1080 affected insns for processing in the subsequent constraint
1081 pass. */
1082 static void
1083 spill_pseudos (HARD_REG_SET set)
1084 {
1085 int i;
1086 bitmap_head to_process;
1087 rtx_insn *insn;
1088
1089 if (hard_reg_set_empty_p (set))
1090 return;
1091 if (lra_dump_file != NULL)
1092 {
1093 fprintf (lra_dump_file, " Spilling non-eliminable hard regs:");
1094 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1095 if (TEST_HARD_REG_BIT (set, i))
1096 fprintf (lra_dump_file, " %d", i);
1097 fprintf (lra_dump_file, "\n");
1098 }
1099 bitmap_initialize (&to_process, ®_obstack);
1100 for (i = FIRST_PSEUDO_REGISTER; i < max_reg_num (); i++)
1101 if (lra_reg_info[i].nrefs != 0 && reg_renumber[i] >= 0
1102 && overlaps_hard_reg_set_p (set,
1103 PSEUDO_REGNO_MODE (i), reg_renumber[i]))
1104 {
1105 if (lra_dump_file != NULL)
1106 fprintf (lra_dump_file, " Spilling r%d(%d)\n",
1107 i, reg_renumber[i]);
1108 reg_renumber[i] = -1;
1109 bitmap_ior_into (&to_process, &lra_reg_info[i].insn_bitmap);
1110 }
1111 lra_no_alloc_regs |= set;
1112 for (insn = get_insns (); insn != NULL_RTX; insn = NEXT_INSN (insn))
1113 if (bitmap_bit_p (&to_process, INSN_UID (insn)))
1114 {
1115 lra_push_insn (insn);
1116 lra_set_used_insn_alternative (insn, LRA_UNKNOWN_ALT);
1117 }
1118 bitmap_clear (&to_process);
1119 }
1120
1121 /* Update all offsets and possibility for elimination on eliminable
1122 registers. Spill pseudos assigned to registers which are
1123 uneliminable, update LRA_NO_ALLOC_REGS and ELIMINABLE_REG_SET. Add
1124 insns to INSNS_WITH_CHANGED_OFFSETS containing eliminable hard
1125 registers whose offsets should be changed. Return true if any
1126 elimination offset changed. */
1127 static bool
1128 update_reg_eliminate (bitmap insns_with_changed_offsets)
1129 {
1130 bool prev, result;
1131 class lra_elim_table *ep, *ep1;
1132 HARD_REG_SET temp_hard_reg_set;
1133
1134 targetm.compute_frame_layout ();
1135
1136 /* Clear self elimination offsets. */
1137 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1138 self_elim_offsets[ep->from] = 0;
1139 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1140 {
1141 /* If it is a currently used elimination: update the previous
1142 offset. */
1143 if (elimination_map[ep->from] == ep)
1144 ep->previous_offset = ep->offset;
1145
1146 prev = ep->prev_can_eliminate;
1147 setup_can_eliminate (ep, targetm.can_eliminate (ep->from, ep->to));
1148 if (ep->can_eliminate && ! prev)
1149 {
1150 /* It is possible that not eliminable register becomes
1151 eliminable because we took other reasons into account to
1152 set up eliminable regs in the initial set up. Just
1153 ignore new eliminable registers. */
1154 setup_can_eliminate (ep, false);
1155 continue;
1156 }
1157 if (ep->can_eliminate != prev && elimination_map[ep->from] == ep)
1158 {
1159 /* We cannot use this elimination anymore -- find another
1160 one. */
1161 if (lra_dump_file != NULL)
1162 fprintf (lra_dump_file,
1163 " Elimination %d to %d is not possible anymore\n",
1164 ep->from, ep->to);
1165 /* If after processing RTL we decides that SP can be used as
1166 a result of elimination, it cannot be changed. */
1167 gcc_assert ((ep->to_rtx != stack_pointer_rtx)
1168 || (ep->from < FIRST_PSEUDO_REGISTER
1169 && fixed_regs [ep->from]));
1170 /* Mark that is not eliminable anymore. */
1171 elimination_map[ep->from] = NULL;
1172 for (ep1 = ep + 1; ep1 < ®_eliminate[NUM_ELIMINABLE_REGS]; ep1++)
1173 if (ep1->can_eliminate && ep1->from == ep->from)
1174 break;
1175 if (ep1 < ®_eliminate[NUM_ELIMINABLE_REGS])
1176 {
1177 if (lra_dump_file != NULL)
1178 fprintf (lra_dump_file, " Using elimination %d to %d now\n",
1179 ep1->from, ep1->to);
1180 lra_assert (known_eq (ep1->previous_offset, 0));
1181 ep1->previous_offset = ep->offset;
1182 }
1183 else
1184 {
1185 /* There is no elimination anymore just use the hard
1186 register `from' itself. Setup self elimination
1187 offset to restore the original offset values. */
1188 if (lra_dump_file != NULL)
1189 fprintf (lra_dump_file, " %d is not eliminable at all\n",
1190 ep->from);
1191 self_elim_offsets[ep->from] = -ep->offset;
1192 if (maybe_ne (ep->offset, 0))
1193 bitmap_ior_into (insns_with_changed_offsets,
1194 &lra_reg_info[ep->from].insn_bitmap);
1195 }
1196 }
1197
1198 INITIAL_ELIMINATION_OFFSET (ep->from, ep->to, ep->offset);
1199 }
1200 setup_elimination_map ();
1201 result = false;
1202 CLEAR_HARD_REG_SET (temp_hard_reg_set);
1203 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1204 if (elimination_map[ep->from] == NULL)
1205 add_to_hard_reg_set (&temp_hard_reg_set, Pmode, ep->from);
1206 else if (elimination_map[ep->from] == ep)
1207 {
1208 /* Prevent the hard register into which we eliminate from
1209 the usage for pseudos. */
1210 if (ep->from != ep->to)
1211 add_to_hard_reg_set (&temp_hard_reg_set, Pmode, ep->to);
1212 if (maybe_ne (ep->previous_offset, ep->offset))
1213 {
1214 bitmap_ior_into (insns_with_changed_offsets,
1215 &lra_reg_info[ep->from].insn_bitmap);
1216
1217 /* Update offset when the eliminate offset have been
1218 changed. */
1219 lra_update_reg_val_offset (lra_reg_info[ep->from].val,
1220 ep->offset - ep->previous_offset);
1221 result = true;
1222 }
1223 }
1224 lra_no_alloc_regs |= temp_hard_reg_set;
1225 eliminable_regset &= ~temp_hard_reg_set;
1226 spill_pseudos (temp_hard_reg_set);
1227 return result;
1228 }
1229
1230 /* Initialize the table of hard registers to eliminate.
1231 Pre-condition: global flag frame_pointer_needed has been set before
1232 calling this function. */
1233 static void
1234 init_elim_table (void)
1235 {
1236 class lra_elim_table *ep;
1237 bool value_p;
1238 const struct elim_table_1 *ep1;
1239
1240 if (!reg_eliminate)
1241 reg_eliminate = XCNEWVEC (class lra_elim_table, NUM_ELIMINABLE_REGS);
1242
1243 memset (self_elim_offsets, 0, sizeof (self_elim_offsets));
1244 /* Initiate member values which will be never changed. */
1245 self_elim_table.can_eliminate = self_elim_table.prev_can_eliminate = true;
1246 self_elim_table.previous_offset = 0;
1247
1248 for (ep = reg_eliminate, ep1 = reg_eliminate_1;
1249 ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++, ep1++)
1250 {
1251 ep->offset = ep->previous_offset = 0;
1252 ep->from = ep1->from;
1253 ep->to = ep1->to;
1254 value_p = (targetm.can_eliminate (ep->from, ep->to)
1255 && ! (ep->to == STACK_POINTER_REGNUM
1256 && frame_pointer_needed
1257 && (! SUPPORTS_STACK_ALIGNMENT
1258 || ! stack_realign_fp)));
1259 setup_can_eliminate (ep, value_p);
1260 }
1261
1262 /* Build the FROM and TO REG rtx's. Note that code in gen_rtx_REG
1263 will cause, e.g., gen_rtx_REG (Pmode, STACK_POINTER_REGNUM) to
1264 equal stack_pointer_rtx. We depend on this. Threfore we switch
1265 off that we are in LRA temporarily. */
1266 lra_in_progress = 0;
1267 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1268 {
1269 ep->from_rtx = gen_rtx_REG (Pmode, ep->from);
1270 ep->to_rtx = gen_rtx_REG (Pmode, ep->to);
1271 eliminable_reg_rtx[ep->from] = ep->from_rtx;
1272 }
1273 lra_in_progress = 1;
1274 }
1275
1276 /* Function for initialization of elimination once per function. It
1277 sets up sp offset for each insn. */
1278 static void
1279 init_elimination (void)
1280 {
1281 bool stop_to_sp_elimination_p;
1282 basic_block bb;
1283 rtx_insn *insn;
1284 class lra_elim_table *ep;
1285
1286 init_elim_table ();
1287 FOR_EACH_BB_FN (bb, cfun)
1288 {
1289 curr_sp_change = 0;
1290 stop_to_sp_elimination_p = false;
1291 FOR_BB_INSNS (bb, insn)
1292 if (INSN_P (insn))
1293 {
1294 lra_get_insn_recog_data (insn)->sp_offset = curr_sp_change;
1295 if (NONDEBUG_INSN_P (insn))
1296 {
1297 mark_not_eliminable (PATTERN (insn), VOIDmode);
1298 if (maybe_ne (curr_sp_change, 0)
1299 && find_reg_note (insn, REG_LABEL_OPERAND, NULL_RTX))
1300 stop_to_sp_elimination_p = true;
1301 }
1302 }
1303 if (! frame_pointer_needed
1304 && (maybe_ne (curr_sp_change, 0) || stop_to_sp_elimination_p)
1305 && bb->succs && bb->succs->length () != 0)
1306 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1307 if (ep->to == STACK_POINTER_REGNUM)
1308 setup_can_eliminate (ep, false);
1309 }
1310 setup_elimination_map ();
1311 }
1312
1313 /* Eliminate hard reg given by its location LOC. */
1314 void
1315 lra_eliminate_reg_if_possible (rtx *loc)
1316 {
1317 int regno;
1318 class lra_elim_table *ep;
1319
1320 lra_assert (REG_P (*loc));
1321 if ((regno = REGNO (*loc)) >= FIRST_PSEUDO_REGISTER
1322 || ! TEST_HARD_REG_BIT (lra_no_alloc_regs, regno))
1323 return;
1324 if ((ep = get_elimination (*loc)) != NULL)
1325 *loc = ep->to_rtx;
1326 }
1327
1328 /* Do (final if FINAL_P or first if FIRST_P) elimination in INSN. Add
1329 the insn for subsequent processing in the constraint pass, update
1330 the insn info. */
1331 static void
1332 process_insn_for_elimination (rtx_insn *insn, bool final_p, bool first_p)
1333 {
1334 eliminate_regs_in_insn (insn, final_p, first_p, 0);
1335 if (! final_p)
1336 {
1337 /* Check that insn changed its code. This is a case when a move
1338 insn becomes an add insn and we do not want to process the
1339 insn as a move anymore. */
1340 int icode = recog (PATTERN (insn), insn, 0);
1341
1342 if (icode >= 0 && icode != INSN_CODE (insn))
1343 {
1344 if (INSN_CODE (insn) >= 0)
1345 /* Insn code is changed. It may change its operand type
1346 from IN to INOUT. Inform the subsequent assignment
1347 subpass about this situation. */
1348 check_and_force_assignment_correctness_p = true;
1349 INSN_CODE (insn) = icode;
1350 lra_update_insn_recog_data (insn);
1351 }
1352 lra_update_insn_regno_info (insn);
1353 lra_push_insn (insn);
1354 lra_set_used_insn_alternative (insn, LRA_UNKNOWN_ALT);
1355 }
1356 }
1357
1358 /* Entry function to do final elimination if FINAL_P or to update
1359 elimination register offsets (FIRST_P if we are doing it the first
1360 time). */
1361 void
1362 lra_eliminate (bool final_p, bool first_p)
1363 {
1364 unsigned int uid;
1365 bitmap_head insns_with_changed_offsets;
1366 bitmap_iterator bi;
1367 class lra_elim_table *ep;
1368
1369 gcc_assert (! final_p || ! first_p);
1370
1371 timevar_push (TV_LRA_ELIMINATE);
1372
1373 if (first_p)
1374 init_elimination ();
1375
1376 bitmap_initialize (&insns_with_changed_offsets, ®_obstack);
1377 if (final_p)
1378 {
1379 if (flag_checking)
1380 {
1381 update_reg_eliminate (&insns_with_changed_offsets);
1382 gcc_assert (bitmap_empty_p (&insns_with_changed_offsets));
1383 }
1384 /* We change eliminable hard registers in insns so we should do
1385 this for all insns containing any eliminable hard
1386 register. */
1387 for (ep = reg_eliminate; ep < ®_eliminate[NUM_ELIMINABLE_REGS]; ep++)
1388 if (elimination_map[ep->from] != NULL)
1389 bitmap_ior_into (&insns_with_changed_offsets,
1390 &lra_reg_info[ep->from].insn_bitmap);
1391 }
1392 else if (! update_reg_eliminate (&insns_with_changed_offsets))
1393 goto lra_eliminate_done;
1394 if (lra_dump_file != NULL)
1395 {
1396 fprintf (lra_dump_file, "New elimination table:\n");
1397 print_elim_table (lra_dump_file);
1398 }
1399 EXECUTE_IF_SET_IN_BITMAP (&insns_with_changed_offsets, 0, uid, bi)
1400 /* A dead insn can be deleted in process_insn_for_elimination. */
1401 if (lra_insn_recog_data[uid] != NULL)
1402 process_insn_for_elimination (lra_insn_recog_data[uid]->insn,
1403 final_p, first_p);
1404 bitmap_clear (&insns_with_changed_offsets);
1405
1406 lra_eliminate_done:
1407 timevar_pop (TV_LRA_ELIMINATE);
1408 }
1409