diff options
-rw-r--r-- | gcc/ChangeLog | 20 | ||||
-rw-r--r-- | gcc/alias.c | 53 | ||||
-rw-r--r-- | gcc/caller-save.c | 27 | ||||
-rw-r--r-- | gcc/expr.c | 9 | ||||
-rw-r--r-- | gcc/function.c | 3 | ||||
-rw-r--r-- | gcc/reload1.c | 26 | ||||
-rw-r--r-- | gcc/rtl.h | 1 |
7 files changed, 111 insertions, 28 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index ab8fd4a8353..cac8e5a6b89 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,23 @@ +2002-06-10 Jeffrey Law <law@redhat.com> + + * alias.c (static_reg_base_value): New to hold RTL for + items allocated once per function for the aliasing code. + (init_alias_once_per_function): Initialize static_reg_base_value. + (init_alias_analysis): Avoid throw-away allocations of RTL by + using pre-computed values in static_reg_base_value. + * function.c (prepare_function_start): Call + init_alias_once_per_function appropriately. + * rtl.h (init_alias_once_per_function): Declare. + * caller-save (init_caller_save): Restructure slightly to + avoid lots of silly RTL generation. + * expr.c (init_expr_once): Likewise. + * reload1.c (reload_cse_regs_1): Allocate throw-away register + RTL object here. Pass it into children. + (reload_cse_simplify_operands): Use passed-in register RTL + object. + (reload_cse_simplify): Pass through throw-away register + RTL object. + 2002-06-10 Daniel Berlin <dberlin@dberlin.org> * Makefile.in (ssa.o): Add dependency on $(RTL_H), which was missing. diff --git a/gcc/alias.c b/gcc/alias.c index c528fcf1552..4969aa6d471 100644 --- a/gcc/alias.c +++ b/gcc/alias.c @@ -156,6 +156,10 @@ static GTY((length ("reg_base_value_size"))) rtx *reg_base_value; static rtx *new_reg_base_value; static unsigned int reg_base_value_size; /* size of reg_base_value array */ +/* Static hunks of RTL used by the aliasing code; these are initialized + once per function to avoid unnecessary RTL allocations. */ +static GTY (()) rtx static_reg_base_value[FIRST_PSEUDO_REGISTER]; + #define REG_BASE_VALUE(X) \ (REGNO (X) < reg_base_value_size \ ? reg_base_value[REGNO (X)] : 0) @@ -2638,6 +2642,43 @@ init_alias_once () alias_sets = splay_tree_new (splay_tree_compare_ints, 0, 0); } +/* Per-function initializer for the aliasing code. + + Allocate RTL for argument and other special use registers once + per function here intead of multiple times per function in + init_alias_analysis. */ + +void +init_alias_once_per_function () +{ + int i; + + /* Generate and mark all hard registers which may contain an address. + The stack, frame and argument pointers may contain an address. + An argument register which can hold a Pmode value may contain + an address even if it is not in BASE_REGS. + + The address expression is VOIDmode for an argument and + Pmode for other registers. */ + + for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) + if (TEST_HARD_REG_BIT (argument_registers, i)) + static_reg_base_value[i] + = gen_rtx_ADDRESS (VOIDmode, gen_rtx_REG (Pmode, i)); + + + static_reg_base_value[STACK_POINTER_REGNUM] + = gen_rtx_ADDRESS (Pmode, stack_pointer_rtx); + static_reg_base_value[ARG_POINTER_REGNUM] + = gen_rtx_ADDRESS (Pmode, arg_pointer_rtx); + static_reg_base_value[FRAME_POINTER_REGNUM] + = gen_rtx_ADDRESS (Pmode, frame_pointer_rtx); +#if HARD_FRAME_POINTER_REGNUM != FRAME_POINTER_REGNUM + static_reg_base_value[HARD_FRAME_POINTER_REGNUM] + = gen_rtx_ADDRESS (Pmode, hard_frame_pointer_rtx); +#endif +} + /* Initialize the aliasing machinery. Initialize the REG_KNOWN_VALUE array. */ @@ -2725,20 +2766,18 @@ init_alias_analysis () for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) if (TEST_HARD_REG_BIT (argument_registers, i)) - new_reg_base_value[i] = gen_rtx_ADDRESS (VOIDmode, - gen_rtx_REG (Pmode, i)); + new_reg_base_value[i] = static_reg_base_value[i]; new_reg_base_value[STACK_POINTER_REGNUM] - = gen_rtx_ADDRESS (Pmode, stack_pointer_rtx); + = static_reg_base_value[STACK_POINTER_REGNUM]; new_reg_base_value[ARG_POINTER_REGNUM] - = gen_rtx_ADDRESS (Pmode, arg_pointer_rtx); + = static_reg_base_value[ARG_POINTER_REGNUM]; new_reg_base_value[FRAME_POINTER_REGNUM] - = gen_rtx_ADDRESS (Pmode, frame_pointer_rtx); + = static_reg_base_value[FRAME_POINTER_REGNUM]; #if HARD_FRAME_POINTER_REGNUM != FRAME_POINTER_REGNUM new_reg_base_value[HARD_FRAME_POINTER_REGNUM] - = gen_rtx_ADDRESS (Pmode, hard_frame_pointer_rtx); + = static_reg_base_value[HARD_FRAME_POINTER_REGNUM]; #endif - /* Walk the insns adding values to the new_reg_base_value array. */ for (insn = get_insns (); insn; insn = NEXT_INSN (insn)) { diff --git a/gcc/caller-save.c b/gcc/caller-save.c index 87a13dc0fad..920bafd241b 100644 --- a/gcc/caller-save.c +++ b/gcc/caller-save.c @@ -115,6 +115,9 @@ init_caller_save () rtx address; int i, j; enum machine_mode mode; + rtx savepat, restpat; + rtx test_reg, test_mem; + rtx saveinsn, restinsn; /* First find all the registers that we need to deal with and all the modes that they can have. If we can't find a mode to use, @@ -179,7 +182,17 @@ init_caller_save () address = addr_reg; /* Next we try to form an insn to save and restore the register. We - see if such an insn is recognized and meets its constraints. */ + see if such an insn is recognized and meets its constraints. + + To avoid lots of unnecessary RTL allocation, we construct all the RTL + once, then modify the memory and register operands in-place. */ + + test_reg = gen_rtx_REG (VOIDmode, 0); + test_mem = gen_rtx_MEM (VOIDmode, address); + savepat = gen_rtx_SET (VOIDmode, test_mem, test_reg); + restpat = gen_rtx_SET (VOIDmode, test_reg, test_mem); + saveinsn = emit_insn (savepat); + restinsn = emit_insn (restpat); start_sequence (); @@ -187,14 +200,14 @@ init_caller_save () for (mode = 0 ; mode < MAX_MACHINE_MODE; mode++) if (HARD_REGNO_MODE_OK (i, mode)) { - rtx mem = gen_rtx_MEM (mode, address); - rtx reg = gen_rtx_REG (mode, i); - rtx savepat = gen_rtx_SET (VOIDmode, mem, reg); - rtx restpat = gen_rtx_SET (VOIDmode, reg, mem); - rtx saveinsn = emit_insn (savepat); - rtx restinsn = emit_insn (restpat); int ok; + /* Update the register number and modes of the register + and memory operand. */ + REGNO (test_reg) = i; + PUT_MODE (test_reg, mode); + PUT_MODE (test_mem, mode); + reg_save_code[i][mode] = recog_memoized (saveinsn); reg_restore_code[i][mode] = recog_memoized (restinsn); diff --git a/gcc/expr.c b/gcc/expr.c index b719956ce87..d7dc5316a26 100644 --- a/gcc/expr.c +++ b/gcc/expr.c @@ -214,6 +214,7 @@ init_expr_once () enum machine_mode mode; int num_clobbers; rtx mem, mem1; + rtx reg; /* Try indexing by frame ptr and try by stack ptr. It is known that on the Convex the stack ptr isn't a valid index. @@ -221,6 +222,10 @@ init_expr_once () mem = gen_rtx_MEM (VOIDmode, stack_pointer_rtx); mem1 = gen_rtx_MEM (VOIDmode, frame_pointer_rtx); + /* A scratch register we can modify in-place below to avoid + useless RTL allocations. */ + reg = gen_rtx_REG (VOIDmode, -1); + insn = rtx_alloc (INSN); pat = gen_rtx_SET (0, NULL_RTX, NULL_RTX); PATTERN (insn) = pat; @@ -229,11 +234,11 @@ init_expr_once () mode = (enum machine_mode) ((int) mode + 1)) { int regno; - rtx reg; direct_load[(int) mode] = direct_store[(int) mode] = 0; PUT_MODE (mem, mode); PUT_MODE (mem1, mode); + PUT_MODE (reg, mode); /* See if there is some register that can be used in this mode and directly loaded or stored from memory. */ @@ -246,7 +251,7 @@ init_expr_once () if (! HARD_REGNO_MODE_OK (regno, mode)) continue; - reg = gen_rtx_REG (mode, regno); + REGNO (reg) = regno; SET_SRC (pat) = mem; SET_DEST (pat) = reg; diff --git a/gcc/function.c b/gcc/function.c index d1f4e89d5c2..96c25636261 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -6208,6 +6208,9 @@ prepare_function_start () /* Initialize the RTL mechanism. */ init_emit (); + /* Do per-function initialization of the alias analyzer. */ + init_alias_once_per_function (); + /* Initialize the queue of pending postincrement and postdecrements, and some other info in expr.c. */ init_expr (); diff --git a/gcc/reload1.c b/gcc/reload1.c index e5b19e9c31c..ca25abff22c 100644 --- a/gcc/reload1.c +++ b/gcc/reload1.c @@ -443,7 +443,7 @@ static rtx inc_for_reload PARAMS ((rtx, rtx, rtx, int)); 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)); -static int reload_cse_simplify_operands PARAMS ((rtx)); +static int reload_cse_simplify_operands PARAMS ((rtx, rtx)); static void reload_combine PARAMS ((void)); static void reload_combine_note_use PARAMS ((rtx *, rtx)); static void reload_combine_note_store PARAMS ((rtx, rtx, void *)); @@ -457,7 +457,7 @@ 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_simplify PARAMS ((rtx)); +static void reload_cse_simplify PARAMS ((rtx, rtx)); void fixup_abnormal_edges PARAMS ((void)); extern void dump_needs PARAMS ((struct insn_chain *)); @@ -7992,8 +7992,9 @@ reload_cse_noop_set_p (set) /* Try to simplify INSN. */ static void -reload_cse_simplify (insn) +reload_cse_simplify (insn, testreg) rtx insn; + rtx testreg; { rtx body = PATTERN (insn); @@ -8021,7 +8022,7 @@ reload_cse_simplify (insn) if (count > 0) apply_change_group (); else - reload_cse_simplify_operands (insn); + reload_cse_simplify_operands (insn, testreg); } else if (GET_CODE (body) == PARALLEL) { @@ -8064,7 +8065,7 @@ reload_cse_simplify (insn) if (count > 0) apply_change_group (); else - reload_cse_simplify_operands (insn); + reload_cse_simplify_operands (insn, testreg); } } @@ -8090,6 +8091,7 @@ reload_cse_regs_1 (first) rtx first; { rtx insn; + rtx testreg = gen_rtx_REG (VOIDmode, -1); cselib_init (); init_alias_analysis (); @@ -8097,7 +8099,7 @@ reload_cse_regs_1 (first) for (insn = first; insn; insn = NEXT_INSN (insn)) { if (INSN_P (insn)) - reload_cse_simplify (insn); + reload_cse_simplify (insn, testreg); cselib_process_insn (insn); } @@ -8268,8 +8270,9 @@ reload_cse_simplify_set (set, insn) hard registers. */ static int -reload_cse_simplify_operands (insn) +reload_cse_simplify_operands (insn, testreg) rtx insn; + rtx testreg; { int i, j; @@ -8289,7 +8292,6 @@ reload_cse_simplify_operands (insn) int *op_alt_regno[MAX_RECOG_OPERANDS]; /* Array of alternatives, sorted in order of decreasing desirability. */ int *alternative_order; - rtx reg = gen_rtx_REG (VOIDmode, -1); extract_insn (insn); @@ -8373,8 +8375,8 @@ reload_cse_simplify_operands (insn) if (! TEST_HARD_REG_BIT (equiv_regs[i], regno)) continue; - REGNO (reg) = regno; - PUT_MODE (reg, mode); + REGNO (testreg) = regno; + PUT_MODE (testreg, mode); /* We found a register equal to this operand. Now look for all alternatives that can accept this register and have not been @@ -8416,10 +8418,10 @@ reload_cse_simplify_operands (insn) alternative yet and the operand being replaced is not a cheap CONST_INT. */ if (op_alt_regno[i][j] == -1 - && reg_fits_class_p (reg, class, 0, mode) + && reg_fits_class_p (testreg, class, 0, mode) && (GET_CODE (recog_data.operand[i]) != CONST_INT || (rtx_cost (recog_data.operand[i], SET) - > rtx_cost (reg, SET)))) + > rtx_cost (testreg, SET)))) { alternative_nregs[j]++; op_alt_regno[i][j] = regno; diff --git a/gcc/rtl.h b/gcc/rtl.h index 314adf1567e..ee4e0939fdb 100644 --- a/gcc/rtl.h +++ b/gcc/rtl.h @@ -2166,6 +2166,7 @@ extern int anti_dependence PARAMS ((rtx, rtx)); extern int output_dependence PARAMS ((rtx, rtx)); extern void mark_constant_function PARAMS ((void)); extern void init_alias_once PARAMS ((void)); +extern void init_alias_once_per_function PARAMS ((void)); extern void init_alias_analysis PARAMS ((void)); extern void end_alias_analysis PARAMS ((void)); extern rtx addr_side_effect_eval PARAMS ((rtx, int, int)); |