diff options
author | Jan Hubicka <jh@suse.cz> | 2002-05-31 13:43:18 +0200 |
---|---|---|
committer | Jan Hubicka <hubicka@gcc.gnu.org> | 2002-05-31 11:43:18 +0000 |
commit | 10d1bb3675d063e88ada643bdaa8f51e01f47e5f (patch) | |
tree | 20d9e9485a82572e2e4ec62cf80c757770eaf93d /gcc/reload1.c | |
parent | 8a72fb761ecbcb9ec734eea3ce550caa08a3d014 (diff) | |
download | gcc-10d1bb3675d063e88ada643bdaa8f51e01f47e5f.zip gcc-10d1bb3675d063e88ada643bdaa8f51e01f47e5f.tar.gz gcc-10d1bb3675d063e88ada643bdaa8f51e01f47e5f.tar.bz2 |
gcse.c (gcse_emit_move_after): New.
* gcse.c (gcse_emit_move_after): New.
(pre_delete, hoist_store): Use it.
* reload1.c (emit_input_reload_insns): Use constrain_operands
instead of constraint_accepts_reg_p to verify optimization.
(constraint_accepts_reg_p): Kill
* reload1.c (reload_cse_delete_noop_set): Kill.
(reload_cse_simplify): use delte_insn_and_edges.
From-SVN: r54105
Diffstat (limited to 'gcc/reload1.c')
-rw-r--r-- | gcc/reload1.c | 124 |
1 files changed, 29 insertions, 95 deletions
diff --git a/gcc/reload1.c b/gcc/reload1.c index 6859570..1ce3199 100644 --- a/gcc/reload1.c +++ b/gcc/reload1.c @@ -440,7 +440,6 @@ static void delete_output_reload PARAMS ((rtx, int, int)); static void delete_address_reloads PARAMS ((rtx, rtx)); static void delete_address_reloads_1 PARAMS ((rtx, rtx, rtx)); static rtx inc_for_reload PARAMS ((rtx, rtx, rtx, int)); -static int constraint_accepts_reg_p PARAMS ((const char *, rtx)); static void reload_cse_regs_1 PARAMS ((rtx)); static int reload_cse_noop_set_p PARAMS ((rtx)); static int reload_cse_simplify_set PARAMS ((rtx, rtx)); @@ -458,7 +457,6 @@ static HOST_WIDE_INT sext_for_mode PARAMS ((enum machine_mode, HOST_WIDE_INT)); static void failed_reload PARAMS ((rtx, int)); static int set_reload_reg PARAMS ((int, int)); -static void reload_cse_delete_noop_set PARAMS ((rtx, rtx)); static void reload_cse_simplify PARAMS ((rtx)); void fixup_abnormal_edges PARAMS ((void)); extern void dump_needs PARAMS ((struct insn_chain *)); @@ -6383,38 +6381,43 @@ emit_input_reload_insns (chain, rl, old, j) && SET_DEST (PATTERN (temp)) == old /* Make sure we can access insn_operand_constraint. */ && asm_noperands (PATTERN (temp)) < 0 - /* This is unsafe if prev insn rejects our reload reg. */ - && constraint_accepts_reg_p (insn_data[recog_memoized (temp)].operand[0].constraint, - reloadreg) /* This is unsafe if operand occurs more than once in current insn. Perhaps some occurrences aren't reloaded. */ - && count_occurrences (PATTERN (insn), old, 0) == 1 - /* Don't risk splitting a matching pair of operands. */ - && ! reg_mentioned_p (old, SET_SRC (PATTERN (temp)))) + && count_occurrences (PATTERN (insn), old, 0) == 1) { + rtx old = SET_DEST (PATTERN (temp)); /* Store into the reload register instead of the pseudo. */ SET_DEST (PATTERN (temp)) = reloadreg; - /* If the previous insn is an output reload, the source is - a reload register, and its spill_reg_store entry will - contain the previous destination. This is now - invalid. */ - if (GET_CODE (SET_SRC (PATTERN (temp))) == REG - && REGNO (SET_SRC (PATTERN (temp))) < FIRST_PSEUDO_REGISTER) + /* Verify that resulting insn is valid. */ + extract_insn (temp); + if (constrain_operands (1)) { - spill_reg_store[REGNO (SET_SRC (PATTERN (temp)))] = 0; - spill_reg_stored_to[REGNO (SET_SRC (PATTERN (temp)))] = 0; - } + /* If the previous insn is an output reload, the source is + a reload register, and its spill_reg_store entry will + contain the previous destination. This is now + invalid. */ + if (GET_CODE (SET_SRC (PATTERN (temp))) == REG + && REGNO (SET_SRC (PATTERN (temp))) < FIRST_PSEUDO_REGISTER) + { + spill_reg_store[REGNO (SET_SRC (PATTERN (temp)))] = 0; + spill_reg_stored_to[REGNO (SET_SRC (PATTERN (temp)))] = 0; + } - /* If these are the only uses of the pseudo reg, - pretend for GDB it lives in the reload reg we used. */ - if (REG_N_DEATHS (REGNO (old)) == 1 - && REG_N_SETS (REGNO (old)) == 1) + /* If these are the only uses of the pseudo reg, + pretend for GDB it lives in the reload reg we used. */ + if (REG_N_DEATHS (REGNO (old)) == 1 + && REG_N_SETS (REGNO (old)) == 1) + { + reg_renumber[REGNO (old)] = REGNO (rl->reg_rtx); + alter_reg (REGNO (old), -1); + } + special = 1; + } + else { - reg_renumber[REGNO (old)] = REGNO (rl->reg_rtx); - alter_reg (REGNO (old), -1); + SET_DEST (PATTERN (temp)) = old; } - special = 1; } } @@ -7980,75 +7983,6 @@ inc_for_reload (reloadreg, in, value, inc_amount) return store; } -/* Return 1 if we are certain that the constraint-string STRING allows - the hard register REG. Return 0 if we can't be sure of this. */ - -static int -constraint_accepts_reg_p (string, reg) - const char *string; - rtx reg; -{ - int value = 0; - int regno = true_regnum (reg); - int c; - - /* Initialize for first alternative. */ - value = 0; - /* Check that each alternative contains `g' or `r'. */ - while (1) - switch (c = *string++) - { - case 0: - /* If an alternative lacks `g' or `r', we lose. */ - return value; - case ',': - /* If an alternative lacks `g' or `r', we lose. */ - if (value == 0) - return 0; - /* Initialize for next alternative. */ - value = 0; - break; - case 'g': - case 'r': - /* Any general reg wins for this alternative. */ - if (TEST_HARD_REG_BIT (reg_class_contents[(int) GENERAL_REGS], regno)) - value = 1; - break; - default: - /* Any reg in specified class wins for this alternative. */ - { - enum reg_class class = REG_CLASS_FROM_LETTER (c); - - if (TEST_HARD_REG_BIT (reg_class_contents[(int) class], regno)) - value = 1; - } - } -} - -/* INSN is a no-op; delete it. - If this sets the return value of the function, we must keep a USE around, - in case this is in a different basic block than the final USE. Otherwise, - we could loose important register lifeness information on - SMALL_REGISTER_CLASSES machines, where return registers might be used as - spills: subsequent passes assume that spill registers are dead at the end - of a basic block. - VALUE must be the return value in such a case, NULL otherwise. */ -static void -reload_cse_delete_noop_set (insn, value) - rtx insn, value; -{ - bool purge = BLOCK_FOR_INSN (insn)->end == insn; - if (value) - { - PATTERN (insn) = gen_rtx_USE (VOIDmode, value); - INSN_CODE (insn) = -1; - REG_NOTES (insn) = NULL_RTX; - } - else - delete_insn (insn); - if (purge) - purge_dead_edges (BLOCK_FOR_INSN (insn)); -} /* See whether a single set SET is a noop. */ static int @@ -8082,7 +8016,7 @@ reload_cse_simplify (insn) if (REG_P (value) && ! REG_FUNCTION_VALUE_P (value)) value = 0; - reload_cse_delete_noop_set (insn, value); + delete_insn_and_edges (insn); return; } @@ -8119,7 +8053,7 @@ reload_cse_simplify (insn) if (i < 0) { - reload_cse_delete_noop_set (insn, value); + delete_insn_and_edges (insn); /* We're done with this insn. */ return; } |