diff options
author | Richard Sandiford <rsandifo@nildram.co.uk> | 2007-05-22 20:52:39 +0000 |
---|---|---|
committer | Richard Sandiford <rsandifo@gcc.gnu.org> | 2007-05-22 20:52:39 +0000 |
commit | 09e18274fda8ab58c3417e148e37d0264df1f6bb (patch) | |
tree | 9e698cb3b5286c709642b8db45a05193e856c5fc | |
parent | 6936461f13040d03e5371a9069fe477ac8a7c705 (diff) | |
download | gcc-09e18274fda8ab58c3417e148e37d0264df1f6bb.zip gcc-09e18274fda8ab58c3417e148e37d0264df1f6bb.tar.gz gcc-09e18274fda8ab58c3417e148e37d0264df1f6bb.tar.bz2 |
regs.h (end_hard_regno): New function.
gcc/
* regs.h (end_hard_regno): New function.
(END_HARD_REGNO, END_REGNO): New macros.
(add_to_hard_reg_set): New function.
(remove_from_hard_reg_set): Likewise.
(in_hard_reg_set_p): Likewise.
(overlaps_hard_reg_set_p): Likewise.
* bt-load.c (find_btr_reference): Use overlaps_hard_reg_set_p.
(note_btr_set): Use END_HARD_REGNO.
* caller-save.c (setup_save_areas): Use end_hard_regno.
(mark_set_regs): Use END_HARD_REGNO.
(add_stored_regs): Use end_hard_regno.
(mark_referenced_regs): Use add_to_hard_reg_set.
* combine.c (update_table_tick): Use END_REGNO.
(record_value_for_reg): Likewise.
(record_dead_and_set_regs): Likewise.
(get_last_value_validate): Likewise.
(use_crosses_set_p): Likewise.
(reg_dead_at_p_1): Likewise.
(reg_dead_at_p): Likewise.
(mark_used_regs_combine): Use add_to_hard_reg_set.
(move_deaths): Use END_HARD_REGNO.
(reg_bitfield_target_p): Use end_hard_regno.
(distribute_notes): Use END_HARD_REGNO.
* cse.c (mention_regs): Use END_REGNO.
(insert): Use add_to_hard_reg_set.
(invalidate): Use END_HARD_REGNO.
(invalidate_for_call): Likewise.
(exp_equiv_p): Use END_REGNO.
(cse_insn): Likewise.
* cselib.c (cselib_invalidate_regno): Use end_hard_regno.
* df-problems.c (df_urec_mark_reg_change): Use END_HARD_REGNO.
* df-scan.c (df_ref_record): Use END_HARD_REGNO.
* function.c (keep_stack_depressed): Use end_hard_regno.
* global.c (global_alloc): Use end_hard_regno.
(global_conflicts): Use add_to_hard_reg_set instead of
mark_reg_live_nc.
(find_reg): Likewise.
(mark_reg_store): Likewise.
(mark_reg_conflicts): Likewise.
(mark_reg_death): Use remove_from_hard_reg_set.
(mark_reg_live_nc): Delete.
(set_preference): Use end_hard_regno.
* local-alloc.c (mark_life): Use add_to_hard_reg_set and
remove_from_hard_reg_set.
(post_mark_life): Use add_to_hard_reg_set.
* mode-switching.c (reg_dies): Use remove_from_hard_reg_set.
(reg_becomes_live): Use add_to_hard_reg_set.
* recog.c (reg_fits_class_p): Use in_hard_reg_set_p.
(peep2_find_free_register): Use add_to_hard_reg_set.
* reg-stack.c (convert_regs_exit): Use END_HARD_REGNO.
* regclass.c (record_reg_classes): Use in_hard_reg_set_p.
* regrename.c (note_sets): Use add_to_hard_reg_set.
(clear_dead_regs): Use remove_from_hard_reg_set.
(regrename_optimize): Use add_to_hard_reg_set.
(find_oldest_value_reg): Use in_hard_reg_set_p.
* reload.c (push_reload): Use in_hard_reg_set_p and end_hard_regno.
(hard_reg_set_here_p): Use end_hard_regno.
(decompose): Likewise.
(reg_overlap_mentioned_for_reload_p): Use END_HARD_REGNO.
(find_equiv_reg): Use in_hard_reg_set_p and end_hard_regno.
* reload1.c (compute_use_by_pseudos): Use add_to_hard_reg_set.
(mark_home_live): Use end_hard_regno.
(spill_hard_reg): Likewise.
(clear_reload_reg_in_use): Likewise.
* reorg.c (delete_prior_computation): Use END_REGNO.
* resource.c (update_live_status): Use END_HARD_REGNO.
(mark_referenced_resources): Use add_to_hard_reg_set.
(mark_set_resources): Likewise.
(mark_target_live_regs): Likewise. Use remove_from_hard_reg_set.
* rtlanal.c (refers_to_regno_p): Use END_REGNO.
(reg_overlap_mentioned_p): Likewise.
(dead_or_set_p): Likewise. Use an exclusive upper loop bound.
(covers_regno_no_parallel_p): Use END_REGNO.
(find_regno_note): Likewise.
(find_reg_fusage): Use END_HARD_REGNO.
* stmt.c (decl_overlaps_hard_reg_set_p): Use overlaps_hard_reg_set_p.
* var-tracking.c (emit_note_insn_var_location): Use end_hard_regno.
From-SVN: r124961
-rw-r--r-- | gcc/ChangeLog | 80 | ||||
-rw-r--r-- | gcc/bt-load.c | 15 | ||||
-rw-r--r-- | gcc/caller-save.c | 13 | ||||
-rw-r--r-- | gcc/combine.c | 53 | ||||
-rw-r--r-- | gcc/cse.c | 29 | ||||
-rw-r--r-- | gcc/cselib.c | 4 | ||||
-rw-r--r-- | gcc/df-problems.c | 6 | ||||
-rw-r--r-- | gcc/df-scan.c | 5 | ||||
-rw-r--r-- | gcc/function.c | 3 | ||||
-rw-r--r-- | gcc/global.c | 60 | ||||
-rw-r--r-- | gcc/local-alloc.c | 11 | ||||
-rw-r--r-- | gcc/mode-switching.c | 12 | ||||
-rw-r--r-- | gcc/recog.c | 21 | ||||
-rw-r--r-- | gcc/reg-stack.c | 3 | ||||
-rw-r--r-- | gcc/regclass.c | 16 | ||||
-rw-r--r-- | gcc/regrename.c | 35 | ||||
-rw-r--r-- | gcc/regs.h | 84 | ||||
-rw-r--r-- | gcc/reload.c | 49 | ||||
-rw-r--r-- | gcc/reload1.c | 17 | ||||
-rw-r--r-- | gcc/reorg.c | 11 | ||||
-rw-r--r-- | gcc/resource.c | 60 | ||||
-rw-r--r-- | gcc/rtlanal.c | 33 | ||||
-rw-r--r-- | gcc/stmt.c | 11 | ||||
-rw-r--r-- | gcc/var-tracking.c | 3 |
24 files changed, 288 insertions, 346 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index e69d30c..45d889b 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,5 +1,85 @@ 2007-05-22 Richard Sandiford <rsandifo@nildram.co.uk> + * regs.h (end_hard_regno): New function. + (END_HARD_REGNO, END_REGNO): New macros. + (add_to_hard_reg_set): New function. + (remove_from_hard_reg_set): Likewise. + (in_hard_reg_set_p): Likewise. + (overlaps_hard_reg_set_p): Likewise. + * bt-load.c (find_btr_reference): Use overlaps_hard_reg_set_p. + (note_btr_set): Use END_HARD_REGNO. + * caller-save.c (setup_save_areas): Use end_hard_regno. + (mark_set_regs): Use END_HARD_REGNO. + (add_stored_regs): Use end_hard_regno. + (mark_referenced_regs): Use add_to_hard_reg_set. + * combine.c (update_table_tick): Use END_REGNO. + (record_value_for_reg): Likewise. + (record_dead_and_set_regs): Likewise. + (get_last_value_validate): Likewise. + (use_crosses_set_p): Likewise. + (reg_dead_at_p_1): Likewise. + (reg_dead_at_p): Likewise. + (mark_used_regs_combine): Use add_to_hard_reg_set. + (move_deaths): Use END_HARD_REGNO. + (reg_bitfield_target_p): Use end_hard_regno. + (distribute_notes): Use END_HARD_REGNO. + * cse.c (mention_regs): Use END_REGNO. + (insert): Use add_to_hard_reg_set. + (invalidate): Use END_HARD_REGNO. + (invalidate_for_call): Likewise. + (exp_equiv_p): Use END_REGNO. + (cse_insn): Likewise. + * cselib.c (cselib_invalidate_regno): Use end_hard_regno. + * df-problems.c (df_urec_mark_reg_change): Use END_HARD_REGNO. + * df-scan.c (df_ref_record): Use END_HARD_REGNO. + * function.c (keep_stack_depressed): Use end_hard_regno. + * global.c (global_alloc): Use end_hard_regno. + (global_conflicts): Use add_to_hard_reg_set instead of + mark_reg_live_nc. + (find_reg): Likewise. + (mark_reg_store): Likewise. + (mark_reg_conflicts): Likewise. + (mark_reg_death): Use remove_from_hard_reg_set. + (mark_reg_live_nc): Delete. + (set_preference): Use end_hard_regno. + * local-alloc.c (mark_life): Use add_to_hard_reg_set and + remove_from_hard_reg_set. + (post_mark_life): Use add_to_hard_reg_set. + * mode-switching.c (reg_dies): Use remove_from_hard_reg_set. + (reg_becomes_live): Use add_to_hard_reg_set. + * recog.c (reg_fits_class_p): Use in_hard_reg_set_p. + (peep2_find_free_register): Use add_to_hard_reg_set. + * reg-stack.c (convert_regs_exit): Use END_HARD_REGNO. + * regclass.c (record_reg_classes): Use in_hard_reg_set_p. + * regrename.c (note_sets): Use add_to_hard_reg_set. + (clear_dead_regs): Use remove_from_hard_reg_set. + (regrename_optimize): Use add_to_hard_reg_set. + (find_oldest_value_reg): Use in_hard_reg_set_p. + * reload.c (push_reload): Use in_hard_reg_set_p and end_hard_regno. + (hard_reg_set_here_p): Use end_hard_regno. + (decompose): Likewise. + (reg_overlap_mentioned_for_reload_p): Use END_HARD_REGNO. + (find_equiv_reg): Use in_hard_reg_set_p and end_hard_regno. + * reload1.c (compute_use_by_pseudos): Use add_to_hard_reg_set. + (mark_home_live): Use end_hard_regno. + (spill_hard_reg): Likewise. + (clear_reload_reg_in_use): Likewise. + * reorg.c (delete_prior_computation): Use END_REGNO. + * resource.c (update_live_status): Use END_HARD_REGNO. + (mark_referenced_resources): Use add_to_hard_reg_set. + (mark_set_resources): Likewise. + (mark_target_live_regs): Likewise. Use remove_from_hard_reg_set. + * rtlanal.c (refers_to_regno_p): Use END_REGNO. + (reg_overlap_mentioned_p): Likewise. + (dead_or_set_p): Likewise. Use an exclusive upper loop bound. + (covers_regno_no_parallel_p): Use END_REGNO. + (find_regno_note): Likewise. + (find_reg_fusage): Use END_HARD_REGNO. + * stmt.c (decl_overlaps_hard_reg_set_p): Use overlaps_hard_reg_set_p. + * var-tracking.c (emit_note_insn_var_location): Use end_hard_regno. + +2007-05-22 Richard Sandiford <rsandifo@nildram.co.uk> + * mode-switching.c (reg_dies): Change type of second argument to "HARD_REG_SET *". (optimize_mode_switching): Update accordingly. diff --git a/gcc/bt-load.c b/gcc/bt-load.c index f5b0782..4a33940 100644 --- a/gcc/bt-load.c +++ b/gcc/bt-load.c @@ -193,20 +193,17 @@ static int find_btr_reference (rtx *px, void *preg) { rtx x; - int regno, i; if (px == preg) return -1; x = *px; if (!REG_P (x)) return 0; - regno = REGNO (x); - for (i = hard_regno_nregs[regno][GET_MODE (x)] - 1; i >= 0; i--) - if (TEST_HARD_REG_BIT (all_btrs, regno+i)) - { - btr_reference_found = px; - return 1; - } + if (overlaps_hard_reg_set_p (all_btrs, GET_MODE (x), REGNO (x))) + { + btr_reference_found = px; + return 1; + } return -1; } @@ -433,7 +430,7 @@ note_btr_set (rtx dest, rtx set ATTRIBUTE_UNUSED, void *data) if (!REG_P (dest)) return; regno = REGNO (dest); - end_regno = regno + hard_regno_nregs[regno][GET_MODE (dest)]; + end_regno = END_HARD_REGNO (dest); for (; regno < end_regno; regno++) if (TEST_HARD_REG_BIT (all_btrs, regno)) { diff --git a/gcc/caller-save.c b/gcc/caller-save.c index 4acb912..22b928e 100644 --- a/gcc/caller-save.c +++ b/gcc/caller-save.c @@ -296,7 +296,7 @@ setup_save_areas (void) { unsigned int regno = reg_renumber[i]; unsigned int endregno - = regno + hard_regno_nregs[regno][GET_MODE (regno_reg_rtx[i])]; + = end_hard_regno (GET_MODE (regno_reg_rtx[i]), regno); for (r = regno; r < endregno; r++) if (call_used_regs[r]) @@ -496,7 +496,6 @@ static void mark_set_regs (rtx reg, rtx setter ATTRIBUTE_UNUSED, void *data) { int regno, endregno, i; - enum machine_mode mode = GET_MODE (reg); HARD_REG_SET *this_insn_sets = data; if (GET_CODE (reg) == SUBREG) @@ -511,7 +510,7 @@ mark_set_regs (rtx reg, rtx setter ATTRIBUTE_UNUSED, void *data) && REGNO (reg) < FIRST_PSEUDO_REGISTER) { regno = REGNO (reg); - endregno = regno + hard_regno_nregs[regno][mode]; + endregno = END_HARD_REGNO (reg); } else return; @@ -551,7 +550,7 @@ add_stored_regs (rtx reg, rtx setter, void *data) return; regno = REGNO (reg) + offset; - endregno = regno + hard_regno_nregs[regno][mode]; + endregno = end_hard_regno (mode, regno); } for (i = regno; i < endregno; i++) @@ -598,11 +597,7 @@ mark_referenced_regs (rtx x) : reg_renumber[regno]); if (hardregno >= 0) - { - int nregs = hard_regno_nregs[hardregno][GET_MODE (x)]; - while (nregs-- > 0) - SET_HARD_REG_BIT (referenced_regs, hardregno + nregs); - } + add_to_hard_reg_set (&referenced_regs, GET_MODE (x), hardregno); /* If this is a pseudo that did not get a hard register, scan its memory location, since it might involve the use of another register, which might be saved. */ diff --git a/gcc/combine.c b/gcc/combine.c index 7589aac..268fa76 100644 --- a/gcc/combine.c +++ b/gcc/combine.c @@ -10796,9 +10796,7 @@ update_table_tick (rtx x) if (code == REG) { unsigned int regno = REGNO (x); - unsigned int endregno - = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (x)] : 1); + unsigned int endregno = END_REGNO (x); unsigned int r; for (r = regno; r < endregno; r++) @@ -10858,9 +10856,7 @@ static void record_value_for_reg (rtx reg, rtx insn, rtx value) { unsigned int regno = REGNO (reg); - unsigned int endregno - = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (reg)] : 1); + unsigned int endregno = END_REGNO (reg); unsigned int i; /* If VALUE contains REG and we have a previous value for REG, substitute @@ -11029,10 +11025,7 @@ record_dead_and_set_regs (rtx insn) && REG_P (XEXP (link, 0))) { unsigned int regno = REGNO (XEXP (link, 0)); - unsigned int endregno - = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (XEXP (link, 0))] - : 1); + unsigned int endregno = END_REGNO (XEXP (link, 0)); for (i = regno; i < endregno; i++) reg_stat[i].last_death = insn; @@ -11231,9 +11224,7 @@ get_last_value_validate (rtx *loc, rtx insn, int tick, int replace) if (REG_P (x)) { unsigned int regno = REGNO (x); - unsigned int endregno - = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (x)] : 1); + unsigned int endregno = END_REGNO (x); unsigned int j; for (j = regno; j < endregno; j++) @@ -11392,8 +11383,7 @@ use_crosses_set_p (rtx x, int from_cuid) if (code == REG) { unsigned int regno = REGNO (x); - unsigned endreg = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (x)] : 1); + unsigned endreg = END_REGNO (x); #ifdef PUSH_ROUNDING /* Don't allow uses of the stack pointer to be moved, @@ -11449,9 +11439,7 @@ reg_dead_at_p_1 (rtx dest, rtx x, void *data ATTRIBUTE_UNUSED) return; regno = REGNO (dest); - endregno = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (dest)] : 1); - + endregno = END_REGNO (dest); if (reg_dead_endregno > regno && reg_dead_regno < endregno) reg_dead_flag = (GET_CODE (x) == CLOBBER) ? 1 : -1; } @@ -11472,10 +11460,7 @@ reg_dead_at_p (rtx reg, rtx insn) /* Set variables for reg_dead_at_p_1. */ reg_dead_regno = REGNO (reg); - reg_dead_endregno = reg_dead_regno + (reg_dead_regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[reg_dead_regno] - [GET_MODE (reg)] - : 1); + reg_dead_endregno = END_REGNO (reg); reg_dead_flag = 0; @@ -11564,8 +11549,6 @@ mark_used_regs_combine (rtx x) If so, mark all of them just like the first. */ if (regno < FIRST_PSEUDO_REGISTER) { - unsigned int endregno, r; - /* None of this applies to the stack, frame or arg pointers. */ if (regno == STACK_POINTER_REGNUM #if FRAME_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM @@ -11577,9 +11560,7 @@ mark_used_regs_combine (rtx x) || regno == FRAME_POINTER_REGNUM) return; - endregno = regno + hard_regno_nregs[regno][GET_MODE (x)]; - for (r = regno; r < endregno; r++) - SET_HARD_REG_BIT (newpat_used_regs, r); + add_to_hard_reg_set (&newpat_used_regs, GET_MODE (x), regno); } return; @@ -11704,11 +11685,8 @@ move_deaths (rtx x, rtx maybe_kill_insn, int from_cuid, rtx to_insn, > GET_MODE_SIZE (GET_MODE (x)))) { unsigned int deadregno = REGNO (XEXP (note, 0)); - unsigned int deadend - = (deadregno + hard_regno_nregs[deadregno] - [GET_MODE (XEXP (note, 0))]); - unsigned int ourend - = regno + hard_regno_nregs[regno][GET_MODE (x)]; + unsigned int deadend = END_HARD_REGNO (XEXP (note, 0)); + unsigned int ourend = END_HARD_REGNO (x); unsigned int i; for (i = deadregno; i < deadend; i++) @@ -11731,8 +11709,7 @@ move_deaths (rtx x, rtx maybe_kill_insn, int from_cuid, rtx to_insn, && regno < FIRST_PSEUDO_REGISTER && hard_regno_nregs[regno][GET_MODE (x)] > 1) { - unsigned int ourend - = regno + hard_regno_nregs[regno][GET_MODE (x)]; + unsigned int ourend = END_HARD_REGNO (x); unsigned int i, offset; rtx oldnotes = 0; @@ -11850,8 +11827,8 @@ reg_bitfield_target_p (rtx x, rtx body) if (tregno >= FIRST_PSEUDO_REGISTER || regno >= FIRST_PSEUDO_REGISTER) return target == x; - endtregno = tregno + hard_regno_nregs[tregno][GET_MODE (target)]; - endregno = regno + hard_regno_nregs[regno][GET_MODE (x)]; + endtregno = end_hard_regno (GET_MODE (target), tregno); + endregno = end_hard_regno (GET_MODE (x), regno); return endregno > tregno && regno < endtregno; } @@ -12352,9 +12329,7 @@ distribute_notes (rtx notes, rtx from_insn, rtx i3, rtx i2, rtx elim_i2, if (place && regno < FIRST_PSEUDO_REGISTER && hard_regno_nregs[regno][GET_MODE (XEXP (note, 0))] > 1) { - unsigned int endregno - = regno + hard_regno_nregs[regno] - [GET_MODE (XEXP (note, 0))]; + unsigned int endregno = END_HARD_REGNO (XEXP (note, 0)); int all_used = 1; unsigned int i; @@ -1045,9 +1045,7 @@ mention_regs (rtx x) if (code == REG) { unsigned int regno = REGNO (x); - unsigned int endregno - = regno + (regno >= FIRST_PSEUDO_REGISTER ? 1 - : hard_regno_nregs[regno][GET_MODE (x)]); + unsigned int endregno = END_REGNO (x); unsigned int i; for (i = regno; i < endregno; i++) @@ -1429,14 +1427,7 @@ insert (rtx x, struct table_elt *classp, unsigned int hash, enum machine_mode mo /* If X is a hard register, show it is being put in the table. */ if (REG_P (x) && REGNO (x) < FIRST_PSEUDO_REGISTER) - { - unsigned int regno = REGNO (x); - unsigned int endregno = regno + hard_regno_nregs[regno][GET_MODE (x)]; - unsigned int i; - - for (i = regno; i < endregno; i++) - SET_HARD_REG_BIT (hard_regs_in_table, i); - } + add_to_hard_reg_set (&hard_regs_in_table, GET_MODE (x), REGNO (x)); /* Put an element for X into the right hash bucket. */ @@ -1739,8 +1730,7 @@ invalidate (rtx x, enum machine_mode full_mode) { HOST_WIDE_INT in_table = TEST_HARD_REG_BIT (hard_regs_in_table, regno); - unsigned int endregno - = regno + hard_regno_nregs[regno][GET_MODE (x)]; + unsigned int endregno = END_HARD_REGNO (x); unsigned int tregno, tendregno, rn; struct table_elt *p, *next; @@ -1766,8 +1756,7 @@ invalidate (rtx x, enum machine_mode full_mode) continue; tregno = REGNO (p->exp); - tendregno - = tregno + hard_regno_nregs[tregno][GET_MODE (p->exp)]; + tendregno = END_HARD_REGNO (p->exp); if (tendregno > regno && tregno < endregno) remove_from_table (p, hash); } @@ -1978,7 +1967,7 @@ invalidate_for_call (void) continue; regno = REGNO (p->exp); - endregno = regno + hard_regno_nregs[regno][GET_MODE (p->exp)]; + endregno = END_HARD_REGNO (p->exp); for (i = regno; i < endregno; i++) if (TEST_HARD_REG_BIT (regs_invalidated_by_call, i)) @@ -2447,9 +2436,7 @@ exp_equiv_p (rtx x, rtx y, int validate, bool for_gcse) { unsigned int regno = REGNO (y); unsigned int i; - unsigned int endregno - = regno + (regno >= FIRST_PSEUDO_REGISTER ? 1 - : hard_regno_nregs[regno][GET_MODE (y)]); + unsigned int endregno = END_REGNO (y); /* If the quantities are not the same, the expressions are not equivalent. If there are and we are not to validate, they @@ -5380,9 +5367,7 @@ cse_insn (rtx insn, rtx libcall_insn) but it knows that reg_tick has been incremented, and it leaves reg_in_table as -1 . */ unsigned int regno = REGNO (x); - unsigned int endregno - = regno + (regno >= FIRST_PSEUDO_REGISTER ? 1 - : hard_regno_nregs[regno][GET_MODE (x)]); + unsigned int endregno = END_REGNO (x); unsigned int i; for (i = regno; i < endregno; i++) diff --git a/gcc/cselib.c b/gcc/cselib.c index d821bcf..b791d9d 100644 --- a/gcc/cselib.c +++ b/gcc/cselib.c @@ -1029,7 +1029,7 @@ cselib_invalidate_regno (unsigned int regno, enum machine_mode mode) else i = regno - max_value_regs; - endregno = regno + hard_regno_nregs[regno][mode]; + endregno = end_hard_regno (mode, regno); } else { @@ -1050,7 +1050,7 @@ cselib_invalidate_regno (unsigned int regno, enum machine_mode mode) unsigned int this_last = i; if (i < FIRST_PSEUDO_REGISTER && v != NULL) - this_last += hard_regno_nregs[i][GET_MODE (v->val_rtx)] - 1; + this_last = end_hard_regno (GET_MODE (v->val_rtx), i) - 1; if (this_last < regno || v == NULL) { diff --git a/gcc/df-problems.c b/gcc/df-problems.c index 385b8fb..ab2ebfc 100644 --- a/gcc/df-problems.c +++ b/gcc/df-problems.c @@ -2259,12 +2259,10 @@ df_urec_mark_reg_change (rtx reg, rtx setter, void *data) if (!REG_P (reg)) return; - - endregno = regno = REGNO (reg); + regno = REGNO (reg); if (regno < FIRST_PSEUDO_REGISTER) { - endregno +=hard_regno_nregs[regno][GET_MODE (reg)]; - + endregno = END_HARD_REGNO (reg); for (i = regno; i < endregno; i++) { bitmap_set_bit (bb_info->kill, i); diff --git a/gcc/df-scan.c b/gcc/df-scan.c index 87d21a4..69ba04d 100644 --- a/gcc/df-scan.c +++ b/gcc/df-scan.c @@ -1093,11 +1093,10 @@ df_ref_record (struct dataflow *dflow, rtx reg, rtx *loc, { regno += subreg_regno_offset (regno, GET_MODE (SUBREG_REG (reg)), SUBREG_BYTE (reg), GET_MODE (reg)); - endregno = subreg_nregs (reg); + endregno = regno + subreg_nregs (reg); } else - endregno = hard_regno_nregs[regno][GET_MODE (reg)]; - endregno += regno; + endregno = END_HARD_REGNO (reg); /* If this is a multiword hardreg, we create some extra datastructures that will enable us to easily build REG_DEAD and REG_UNUSED notes. */ diff --git a/gcc/function.c b/gcc/function.c index 996d0ab..8338894 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -4771,8 +4771,7 @@ keep_stack_depressed (rtx insns) && !REGNO_REG_SET_P (EXIT_BLOCK_PTR->il.rtl->global_live_at_start, regno) && !refers_to_regno_p (regno, - regno + hard_regno_nregs[regno] - [Pmode], + end_hard_regno (Pmode, regno), info.equiv_reg_src, NULL) && info.const_equiv[regno] == 0) break; diff --git a/gcc/global.c b/gcc/global.c index fd94760..a3da8a2 100644 --- a/gcc/global.c +++ b/gcc/global.c @@ -306,7 +306,6 @@ static void mark_reg_store (rtx, rtx, void *); static void mark_reg_clobber (rtx, rtx, void *); static void mark_reg_conflicts (rtx); static void mark_reg_death (rtx); -static void mark_reg_live_nc (int, enum machine_mode); static void set_preference (rtx, rtx); static void dump_conflicts (FILE *); static void reg_becomes_live (rtx, rtx, void *); @@ -529,7 +528,7 @@ global_alloc (void) if (reg_renumber[i] >= 0) { int regno = reg_renumber[i]; - int endregno = regno + hard_regno_nregs[regno][PSEUDO_REGNO_MODE (i)]; + int endregno = end_hard_regno (PSEUDO_REGNO_MODE (i), regno); int j; for (j = regno; j < endregno; j++) @@ -737,7 +736,7 @@ global_conflicts (void) block_start_allocnos[ax++] = a; } else if ((a = reg_renumber[i]) >= 0) - mark_reg_live_nc (a, PSEUDO_REGNO_MODE (i)); + add_to_hard_reg_set (&hard_regs_live, PSEUDO_REGNO_MODE (i), a); } /* Record that each allocno now live conflicts with each hard reg @@ -1132,7 +1131,7 @@ find_reg (int num, HARD_REG_SET losers, int alt_regs_p, int accept_call_clobbere || ! HARD_REGNO_CALL_PART_CLOBBERED (regno, mode))) { int j; - int lim = regno + hard_regno_nregs[regno][mode]; + int lim = end_hard_regno (mode, regno); for (j = regno + 1; (j < lim && ! TEST_HARD_REG_BIT (used, j)); @@ -1177,7 +1176,7 @@ find_reg (int num, HARD_REG_SET losers, int alt_regs_p, int accept_call_clobbere REGNO_REG_CLASS (i)))) { int j; - int lim = i + hard_regno_nregs[i][mode]; + int lim = end_hard_regno (mode, i); for (j = i + 1; (j < lim && ! TEST_HARD_REG_BIT (used, j) @@ -1213,7 +1212,7 @@ find_reg (int num, HARD_REG_SET losers, int alt_regs_p, int accept_call_clobbere REGNO_REG_CLASS (i)))) { int j; - int lim = i + hard_regno_nregs[i][mode]; + int lim = end_hard_regno (mode, i); for (j = i + 1; (j < lim && ! TEST_HARD_REG_BIT (used, j) @@ -1339,7 +1338,7 @@ find_reg (int num, HARD_REG_SET losers, int alt_regs_p, int accept_call_clobbere { int r = reg_renumber[k]; int endregno - = r + hard_regno_nregs[r][PSEUDO_REGNO_MODE (k)]; + = end_hard_regno (PSEUDO_REGNO_MODE (k), r); if (regno >= r && regno < endregno) { @@ -1374,7 +1373,7 @@ find_reg (int num, HARD_REG_SET losers, int alt_regs_p, int accept_call_clobbere /* Make a set of the hard regs being allocated. */ CLEAR_HARD_REG_SET (this_reg); - lim = best_reg + hard_regno_nregs[best_reg][mode]; + lim = end_hard_regno (mode, best_reg); for (j = best_reg; j < lim; j++) { SET_HARD_REG_BIT (this_reg, j); @@ -1555,7 +1554,7 @@ mark_reg_store (rtx reg, rtx setter, void *data ATTRIBUTE_UNUSED) /* Handle hardware regs (and pseudos allocated to hard regs). */ if (regno < FIRST_PSEUDO_REGISTER && ! fixed_regs[regno]) { - int last = regno + hard_regno_nregs[regno][GET_MODE (reg)]; + int last = end_hard_regno (GET_MODE (reg), regno); while (regno < last) { record_one_conflict (regno); @@ -1604,7 +1603,7 @@ mark_reg_conflicts (rtx reg) /* Handle hardware regs (and pseudos allocated to hard regs). */ if (regno < FIRST_PSEUDO_REGISTER && ! fixed_regs[regno]) { - int last = regno + hard_regno_nregs[regno][GET_MODE (reg)]; + int last = end_hard_regno (GET_MODE (reg), regno); while (regno < last) { record_one_conflict (regno); @@ -1635,32 +1634,9 @@ mark_reg_death (rtx reg) /* Handle hardware regs (and pseudos allocated to hard regs). */ if (regno < FIRST_PSEUDO_REGISTER && ! fixed_regs[regno]) - { - /* Pseudo regs already assigned hardware regs are treated - almost the same as explicit hardware regs. */ - int last = regno + hard_regno_nregs[regno][GET_MODE (reg)]; - while (regno < last) - { - CLEAR_HARD_REG_BIT (hard_regs_live, regno); - regno++; - } - } -} - -/* Mark hard reg REGNO as currently live, assuming machine mode MODE - for the value stored in it. MODE determines how many consecutive - registers are actually in use. Do not record conflicts; - it is assumed that the caller will do that. */ - -static void -mark_reg_live_nc (int regno, enum machine_mode mode) -{ - int last = regno + hard_regno_nregs[regno][mode]; - while (regno < last) - { - SET_HARD_REG_BIT (hard_regs_live, regno); - regno++; - } + /* Pseudo regs already assigned hardware regs are treated + almost the same as explicit hardware regs. */ + remove_from_hard_reg_set (&hard_regs_live, GET_MODE (reg), regno); } /* Try to set a preference for an allocno to a hard register. @@ -1675,7 +1651,7 @@ mark_reg_live_nc (int regno, enum machine_mode mode) static void set_preference (rtx dest, rtx src) { - unsigned int src_regno, dest_regno; + unsigned int src_regno, dest_regno, end_regno; /* Amount to add to the hard regno for SRC, or subtract from that for DEST, to compensate for subregs in SRC or DEST. */ int offset = 0; @@ -1747,9 +1723,8 @@ set_preference (rtx dest, rtx src) SET_REGBIT (hard_reg_preferences, reg_allocno[src_regno], dest_regno); - for (i = dest_regno; - i < dest_regno + hard_regno_nregs[dest_regno][GET_MODE (dest)]; - i++) + end_regno = end_hard_regno (GET_MODE (dest), dest_regno); + for (i = dest_regno; i < end_regno; i++) SET_REGBIT (hard_reg_full_preferences, reg_allocno[src_regno], i); } } @@ -1766,9 +1741,8 @@ set_preference (rtx dest, rtx src) SET_REGBIT (hard_reg_preferences, reg_allocno[dest_regno], src_regno); - for (i = src_regno; - i < src_regno + hard_regno_nregs[src_regno][GET_MODE (src)]; - i++) + end_regno = end_hard_regno (GET_MODE (src), src_regno); + for (i = src_regno; i < end_regno; i++) SET_REGBIT (hard_reg_full_preferences, reg_allocno[dest_regno], i); } } diff --git a/gcc/local-alloc.c b/gcc/local-alloc.c index cd1c01d..01d107e 100644 --- a/gcc/local-alloc.c +++ b/gcc/local-alloc.c @@ -2363,13 +2363,10 @@ find_free_reg (enum reg_class class, enum machine_mode mode, int qtyno, static void mark_life (int regno, enum machine_mode mode, int life) { - int j = hard_regno_nregs[regno][mode]; if (life) - while (--j >= 0) - SET_HARD_REG_BIT (regs_live, regno + j); + add_to_hard_reg_set (®s_live, mode, regno); else - while (--j >= 0) - CLEAR_HARD_REG_BIT (regs_live, regno + j); + remove_from_hard_reg_set (®s_live, mode, regno); } /* Mark register number REGNO (with machine-mode MODE) as live (if LIFE @@ -2380,12 +2377,10 @@ static void post_mark_life (int regno, enum machine_mode mode, int life, int birth, int death) { - int j = hard_regno_nregs[regno][mode]; HARD_REG_SET this_reg; CLEAR_HARD_REG_SET (this_reg); - while (--j >= 0) - SET_HARD_REG_BIT (this_reg, regno + j); + add_to_hard_reg_set (&this_reg, mode, regno); if (life) while (birth < death) diff --git a/gcc/mode-switching.c b/gcc/mode-switching.c index 1d4a751..448192a 100644 --- a/gcc/mode-switching.c +++ b/gcc/mode-switching.c @@ -162,16 +162,14 @@ make_preds_opaque (basic_block b, int j) static void reg_dies (rtx reg, HARD_REG_SET *live) { - int regno, nregs; + int regno; if (!REG_P (reg)) return; regno = REGNO (reg); if (regno < FIRST_PSEUDO_REGISTER) - for (nregs = hard_regno_nregs[regno][GET_MODE (reg)] - 1; nregs >= 0; - nregs--) - CLEAR_HARD_REG_BIT (*live, regno + nregs); + remove_from_hard_reg_set (live, GET_MODE (reg), regno); } /* Record in LIVE that register REG became live. @@ -180,7 +178,7 @@ reg_dies (rtx reg, HARD_REG_SET *live) static void reg_becomes_live (rtx reg, rtx setter ATTRIBUTE_UNUSED, void *live) { - int regno, nregs; + int regno; if (GET_CODE (reg) == SUBREG) reg = SUBREG_REG (reg); @@ -190,9 +188,7 @@ reg_becomes_live (rtx reg, rtx setter ATTRIBUTE_UNUSED, void *live) regno = REGNO (reg); if (regno < FIRST_PSEUDO_REGISTER) - for (nregs = hard_regno_nregs[regno][GET_MODE (reg)] - 1; nregs >= 0; - nregs--) - SET_HARD_REG_BIT (* (HARD_REG_SET *) live, regno + nregs); + add_to_hard_reg_set ((HARD_REG_SET *) live, GET_MODE (reg), regno); } /* Make sure if MODE_ENTRY is defined the MODE_EXIT is defined diff --git a/gcc/recog.c b/gcc/recog.c index 5e1df5c..1b81704 100644 --- a/gcc/recog.c +++ b/gcc/recog.c @@ -2713,21 +2713,9 @@ reg_fits_class_p (rtx operand, enum reg_class cl, int offset, if (cl == NO_REGS) return 0; - if (regno < FIRST_PSEUDO_REGISTER - && TEST_HARD_REG_BIT (reg_class_contents[(int) cl], - regno + offset)) - { - int sr; - regno += offset; - for (sr = hard_regno_nregs[regno][mode] - 1; - sr > 0; sr--) - if (! TEST_HARD_REG_BIT (reg_class_contents[(int) cl], - regno + sr)) - break; - return sr == 0; - } - - return 0; + return (regno < FIRST_PSEUDO_REGISTER + && in_hard_reg_set_p (reg_class_contents[(int) cl], + mode, regno + offset)); } /* Split single instruction. Helper function for split_all_insns and @@ -3054,8 +3042,7 @@ peep2_find_free_register (int from, int to, const char *class_str, } if (success) { - for (j = hard_regno_nregs[regno][mode] - 1; j >= 0; j--) - SET_HARD_REG_BIT (*reg_set, regno + j); + add_to_hard_reg_set (reg_set, mode, regno); /* Start the next search with the next register. */ if (++raw_regno >= FIRST_PSEUDO_REGISTER) diff --git a/gcc/reg-stack.c b/gcc/reg-stack.c index 5a8d8bf..8124013 100644 --- a/gcc/reg-stack.c +++ b/gcc/reg-stack.c @@ -2625,8 +2625,7 @@ convert_regs_exit (void) if (retvalue) { value_reg_low = REGNO (retvalue); - value_reg_high = value_reg_low - + hard_regno_nregs[value_reg_low][GET_MODE (retvalue)] - 1; + value_reg_high = END_HARD_REGNO (retvalue) - 1; } output_stack = &BLOCK_INFO (EXIT_BLOCK_PTR)->stack_in; diff --git a/gcc/regclass.c b/gcc/regclass.c index 1067f93..635f2d3 100644 --- a/gcc/regclass.c +++ b/gcc/regclass.c @@ -1766,7 +1766,6 @@ record_reg_classes (int n_alts, int n_ops, rtx *ops, unsigned int regno = REGNO (ops[!i]); enum machine_mode mode = GET_MODE (ops[!i]); int class; - unsigned int nr; if (regno >= FIRST_PSEUDO_REGISTER && reg_pref != 0 && reg_pref[regno].prefclass != NO_REGS) @@ -1785,18 +1784,9 @@ record_reg_classes (int n_alts, int n_ops, rtx *ops, { if (reg_class_size[class] == 1) op_costs[i].cost[class] = -1; - else - { - for (nr = 0; nr < (unsigned) hard_regno_nregs[regno][mode]; nr++) - { - if (! TEST_HARD_REG_BIT (reg_class_contents[class], - regno + nr)) - break; - } - - if (nr == (unsigned) hard_regno_nregs[regno][mode]) - op_costs[i].cost[class] = -1; - } + else if (in_hard_reg_set_p (reg_class_contents[class], + mode, regno)) + op_costs[i].cost[class] = -1; } } } diff --git a/gcc/regrename.c b/gcc/regrename.c index c55f9c4..6cabe43 100644 --- a/gcc/regrename.c +++ b/gcc/regrename.c @@ -100,21 +100,14 @@ static void note_sets (rtx x, rtx set ATTRIBUTE_UNUSED, void *data) { HARD_REG_SET *pset = (HARD_REG_SET *) data; - unsigned int regno; - int nregs; if (GET_CODE (x) == SUBREG) x = SUBREG_REG (x); if (!REG_P (x)) return; - regno = REGNO (x); - nregs = hard_regno_nregs[regno][GET_MODE (x)]; - /* There must not be pseudos at this point. */ - gcc_assert (regno + nregs <= FIRST_PSEUDO_REGISTER); - - while (nregs-- > 0) - SET_HARD_REG_BIT (*pset, regno + nregs); + gcc_assert (HARD_REGISTER_P (x)); + add_to_hard_reg_set (pset, GET_MODE (x), REGNO (x)); } /* Clear all registers from *PSET for which a note of kind KIND can be found @@ -128,14 +121,9 @@ clear_dead_regs (HARD_REG_SET *pset, enum machine_mode kind, rtx notes) if (REG_NOTE_KIND (note) == kind && REG_P (XEXP (note, 0))) { rtx reg = XEXP (note, 0); - unsigned int regno = REGNO (reg); - int nregs = hard_regno_nregs[regno][GET_MODE (reg)]; - /* There must not be pseudos at this point. */ - gcc_assert (regno + nregs <= FIRST_PSEUDO_REGISTER); - - while (nregs-- > 0) - CLEAR_HARD_REG_BIT (*pset, regno + nregs); + gcc_assert (HARD_REGISTER_P (reg)); + remove_from_hard_reg_set (pset, GET_MODE (reg), REGNO (reg)); } } @@ -218,14 +206,9 @@ regrename_optimize (void) /* Don't clobber traceback for noreturn functions. */ if (frame_pointer_needed) { - int i; - - for (i = hard_regno_nregs[FRAME_POINTER_REGNUM][Pmode]; i--;) - SET_HARD_REG_BIT (unavailable, FRAME_POINTER_REGNUM + i); - + add_to_hard_reg_set (&unavailable, Pmode, FRAME_POINTER_REGNUM); #if FRAME_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM - for (i = hard_regno_nregs[HARD_FRAME_POINTER_REGNUM][Pmode]; i--;) - SET_HARD_REG_BIT (unavailable, HARD_FRAME_POINTER_REGNUM + i); + add_to_hard_reg_set (&unavailable, Pmode, HARD_FRAME_POINTER_REGNUM); #endif } @@ -1388,11 +1371,9 @@ find_oldest_value_reg (enum reg_class cl, rtx reg, struct value_data *vd) { enum machine_mode oldmode = vd->e[i].mode; rtx new; - unsigned int last; - for (last = i; last < i + hard_regno_nregs[i][mode]; last++) - if (!TEST_HARD_REG_BIT (reg_class_contents[cl], last)) - return NULL_RTX; + if (!in_hard_reg_set_p (reg_class_contents[cl], mode, i)) + return NULL_RTX; new = maybe_mode_change (oldmode, vd->e[regno].mode, mode, i, regno); if (new) @@ -243,4 +243,88 @@ extern void clear_reg_info_regno (unsigned int); /* Specify number of hard registers given machine mode occupy. */ extern unsigned char hard_regno_nregs[FIRST_PSEUDO_REGISTER][MAX_MACHINE_MODE]; +/* Return an exclusive upper bound on the registers occupied by hard + register (reg:MODE REGNO). */ + +static inline unsigned int +end_hard_regno (enum machine_mode mode, unsigned int regno) +{ + return regno + hard_regno_nregs[regno][(int) mode]; +} + +/* Likewise for hard register X. */ + +#define END_HARD_REGNO(X) end_hard_regno (GET_MODE (X), REGNO (X)) + +/* Likewise for hard or pseudo register X. */ + +#define END_REGNO(X) (HARD_REGISTER_P (X) ? END_HARD_REGNO (X) : REGNO (X) + 1) + +/* Add to REGS all the registers required to store a value of mode MODE + in register REGNO. */ + +static inline void +add_to_hard_reg_set (HARD_REG_SET *regs, enum machine_mode mode, + unsigned int regno) +{ + unsigned int end_regno; + + end_regno = end_hard_regno (mode, regno); + do + SET_HARD_REG_BIT (*regs, regno); + while (++regno < end_regno); +} + +/* Likewise, but remove the registers. */ + +static inline void +remove_from_hard_reg_set (HARD_REG_SET *regs, enum machine_mode mode, + unsigned int regno) +{ + unsigned int end_regno; + + end_regno = end_hard_regno (mode, regno); + do + CLEAR_HARD_REG_BIT (*regs, regno); + while (++regno < end_regno); +} + +/* Return true if REGS contains the whole of (reg:MODE REGNO). */ + +static inline bool +in_hard_reg_set_p (const HARD_REG_SET regs, enum machine_mode mode, + unsigned int regno) +{ + unsigned int end_regno; + + if (!TEST_HARD_REG_BIT (regs, regno)) + return false; + + end_regno = end_hard_regno (mode, regno); + while (++regno < end_regno) + if (!TEST_HARD_REG_BIT (regs, regno)) + return false; + + return true; +} + +/* Return true if (reg:MODE REGNO) includes an element of REGS. */ + +static inline bool +overlaps_hard_reg_set_p (const HARD_REG_SET regs, enum machine_mode mode, + unsigned int regno) +{ + unsigned int end_regno; + + if (TEST_HARD_REG_BIT (regs, regno)) + return true; + + end_regno = end_hard_regno (mode, regno); + while (++regno < end_regno) + if (TEST_HARD_REG_BIT (regs, regno)) + return true; + + return false; +} + #endif /* GCC_REGS_H */ diff --git a/gcc/reload.c b/gcc/reload.c index 243b65b..16a7e47 100644 --- a/gcc/reload.c +++ b/gcc/reload.c @@ -1259,17 +1259,8 @@ push_reload (rtx in, rtx out, rtx *inloc, rtx *outloc, } for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) if (HARD_REGNO_MODE_OK (i, mode) - && TEST_HARD_REG_BIT (reg_class_contents[(int) class], i)) - { - int nregs = hard_regno_nregs[i][mode]; - - int j; - for (j = 1; j < nregs; j++) - if (! TEST_HARD_REG_BIT (reg_class_contents[(int) class], i + j)) - break; - if (j == nregs) - break; - } + && in_hard_reg_set_p (reg_class_contents[(int) class], mode, i)) + break; if (i == FIRST_PSEUDO_REGISTER) { error_for_asm (this_insn, "impossible register constraint " @@ -1533,18 +1524,15 @@ push_reload (rtx in, rtx out, rtx *inloc, rtx *outloc, || ! bitmap_bit_p (ENTRY_BLOCK_PTR->il.rtl->global_live_at_end, ORIGINAL_REGNO (XEXP (note, 0)))) && ! refers_to_regno_for_reload_p (regno, - (regno - + hard_regno_nregs[regno] - [rel_mode]), + end_hard_regno (rel_mode, + regno), PATTERN (this_insn), inloc) /* If this is also an output reload, IN cannot be used as the reload register if it is set in this insn unless IN is also OUT. */ && (out == 0 || in == out || ! hard_reg_set_here_p (regno, - (regno - + hard_regno_nregs[regno] - [rel_mode]), + end_hard_regno (rel_mode, regno), PATTERN (this_insn))) /* ??? Why is this code so different from the previous? Is there any simple coherent way to describe the two together? @@ -1573,8 +1561,7 @@ push_reload (rtx in, rtx out, rtx *inloc, rtx *outloc, if (offs == nregs && (! (refers_to_regno_for_reload_p - (regno, (regno + hard_regno_nregs[regno][inmode]), - in, (rtx *)0)) + (regno, end_hard_regno (inmode, regno), in, (rtx *) 0)) || can_reload_into (in, regno, inmode))) { rld[i].reg_rtx = gen_rtx_REG (rel_mode, regno); @@ -2089,7 +2076,7 @@ hard_reg_set_here_p (unsigned int beg_regno, unsigned int end_regno, rtx x) /* See if this reg overlaps range under consideration. */ if (r < end_regno - && r + hard_regno_nregs[r][GET_MODE (op0)] > beg_regno) + && end_hard_regno (GET_MODE (op0), r) > beg_regno) return 1; } } @@ -2409,7 +2396,7 @@ decompose (rtx x) } else /* A hard reg. */ - val.end = val.start + hard_regno_nregs[val.start][GET_MODE (x)]; + val.end = end_hard_regno (GET_MODE (x), val.start); break; case SUBREG: @@ -6500,7 +6487,7 @@ reg_overlap_mentioned_for_reload_p (rtx x, rtx in) return 0; } - endregno = regno + hard_regno_nregs[regno][GET_MODE (x)]; + endregno = END_HARD_REGNO (x); return refers_to_regno_for_reload_p (regno, endregno, in, (rtx*) 0); } @@ -6733,17 +6720,9 @@ find_equiv_reg (rtx goal, rtx insn, enum reg_class class, int other, } else if ((unsigned) valueno >= FIRST_PSEUDO_REGISTER) continue; - else - { - int i; - - for (i = hard_regno_nregs[valueno][mode] - 1; i >= 0; i--) - if (! TEST_HARD_REG_BIT (reg_class_contents[(int) class], - valueno + i)) - break; - if (i >= 0) - continue; - } + else if (!in_hard_reg_set_p (reg_class_contents[(int) class], + mode, valueno)) + continue; value = valtry; where = p; break; @@ -6777,9 +6756,7 @@ find_equiv_reg (rtx goal, rtx insn, enum reg_class class, int other, and is also a register that appears in the address of GOAL. */ if (goal_mem && value == SET_DEST (single_set (where)) - && refers_to_regno_for_reload_p (valueno, - (valueno - + hard_regno_nregs[valueno][mode]), + && refers_to_regno_for_reload_p (valueno, end_hard_regno (mode, valueno), goal, (rtx*) 0)) return 0; diff --git a/gcc/reload1.c b/gcc/reload1.c index 4d0251d..7a3e78a 100644 --- a/gcc/reload1.c +++ b/gcc/reload1.c @@ -542,7 +542,6 @@ compute_use_by_pseudos (HARD_REG_SET *to, regset from) EXECUTE_IF_SET_IN_REG_SET (from, FIRST_PSEUDO_REGISTER, regno, rsi) { int r = reg_renumber[regno]; - int nregs; if (r < 0) { @@ -553,11 +552,7 @@ compute_use_by_pseudos (HARD_REG_SET *to, regset from) gcc_assert (reload_completed); } else - { - nregs = hard_regno_nregs[r][PSEUDO_REGNO_MODE (regno)]; - while (nregs-- > 0) - SET_HARD_REG_BIT (*to, r + nregs); - } + add_to_hard_reg_set (to, PSEUDO_REGNO_MODE (regno), r); } } @@ -2194,7 +2189,7 @@ mark_home_live (int regno) i = reg_renumber[regno]; if (i < 0) return; - lim = i + hard_regno_nregs[i][PSEUDO_REGNO_MODE (regno)]; + lim = end_hard_regno (PSEUDO_REGNO_MODE (regno), i); while (i < lim) regs_ever_live[i++] = 1; } @@ -3763,10 +3758,7 @@ spill_hard_reg (unsigned int regno, int cant_eliminate) for (i = FIRST_PSEUDO_REGISTER; i < max_regno; i++) if (reg_renumber[i] >= 0 && (unsigned int) reg_renumber[i] <= regno - && ((unsigned int) reg_renumber[i] - + hard_regno_nregs[(unsigned int) reg_renumber[i]] - [PSEUDO_REGNO_MODE (i)] - > regno)) + && end_hard_regno (PSEUDO_REGNO_MODE (i), reg_renumber[i]) > regno) SET_REGNO_REG_SET (&spilled_pseudos, i); } @@ -4586,8 +4578,7 @@ clear_reload_reg_in_use (unsigned int regno, int opnum, { unsigned int conflict_start = true_regnum (rld[i].reg_rtx); unsigned int conflict_end - = (conflict_start - + hard_regno_nregs[conflict_start][rld[i].mode]); + = end_hard_regno (rld[i].mode, conflict_start); /* If there is an overlap with the first to-be-freed register, adjust the interval start. */ diff --git a/gcc/reorg.c b/gcc/reorg.c index de3219d..bdf2c31 100644 --- a/gcc/reorg.c +++ b/gcc/reorg.c @@ -3170,16 +3170,9 @@ delete_prior_computation (rtx note, rtx insn) && REG_P (SET_DEST (pat))) { int dest_regno = REGNO (SET_DEST (pat)); - int dest_endregno - = (dest_regno - + (dest_regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[dest_regno] - [GET_MODE (SET_DEST (pat))] : 1)); + int dest_endregno = END_REGNO (SET_DEST (pat)); int regno = REGNO (reg); - int endregno - = (regno - + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (reg)] : 1)); + int endregno = END_REGNO (reg); if (dest_regno >= regno && dest_endregno <= endregno) diff --git a/gcc/resource.c b/gcc/resource.c index 5222d18..2e3f3d4 100644 --- a/gcc/resource.c +++ b/gcc/resource.c @@ -107,8 +107,7 @@ update_live_status (rtx dest, rtx x, void *data ATTRIBUTE_UNUSED) else { first_regno = REGNO (dest); - last_regno - = first_regno + hard_regno_nregs[first_regno][GET_MODE (dest)]; + last_regno = END_HARD_REGNO (dest); } if (GET_CODE (x) == CLOBBER) @@ -244,15 +243,8 @@ mark_referenced_resources (rtx x, struct resources *res, return; case REG: - { - unsigned int regno = REGNO (x); - unsigned int last_regno - = regno + hard_regno_nregs[regno][GET_MODE (x)]; - - gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER); - for (r = regno; r < last_regno; r++) - SET_HARD_REG_BIT (res->regs, r); - } + gcc_assert (HARD_REGISTER_P (x)); + add_to_hard_reg_set (&res->regs, GET_MODE (x), REGNO (x)); return; case MEM: @@ -780,13 +772,8 @@ mark_set_resources (rtx x, struct resources *res, int in_dest, case REG: if (in_dest) { - unsigned int regno = REGNO (x); - unsigned int last_regno - = regno + hard_regno_nregs[regno][GET_MODE (x)]; - - gcc_assert (last_regno <= FIRST_PSEUDO_REGISTER); - for (r = regno; r < last_regno; r++) - SET_HARD_REG_BIT (res->regs, r); + gcc_assert (HARD_REGISTER_P (x)); + add_to_hard_reg_set (&res->regs, GET_MODE (x), REGNO (x)); } return; @@ -970,8 +957,6 @@ mark_target_live_regs (rtx insns, rtx target, struct resources *res) if (b != -1) { regset regs_live = BASIC_BLOCK (b)->il.rtl->global_live_at_start; - unsigned int j; - unsigned int regno; rtx start_insn, stop_insn; reg_set_iterator rsi; @@ -984,13 +969,8 @@ mark_target_live_regs (rtx insns, rtx target, struct resources *res) EXECUTE_IF_SET_IN_REG_SET (regs_live, FIRST_PSEUDO_REGISTER, i, rsi) { if (reg_renumber[i] >= 0) - { - regno = reg_renumber[i]; - for (j = regno; - j < regno + hard_regno_nregs[regno][PSEUDO_REGNO_MODE (i)]; - j++) - SET_HARD_REG_BIT (current_live_regs, j); - } + add_to_hard_reg_set (¤t_live_regs, PSEUDO_REGNO_MODE (i), + reg_renumber[i]); } /* Get starting and ending insn, handling the case where each might @@ -1056,16 +1036,9 @@ mark_target_live_regs (rtx insns, rtx target, struct resources *res) if (REG_NOTE_KIND (link) == REG_DEAD && REG_P (XEXP (link, 0)) && REGNO (XEXP (link, 0)) < FIRST_PSEUDO_REGISTER) - { - unsigned int first_regno = REGNO (XEXP (link, 0)); - unsigned int last_regno - = (first_regno - + hard_regno_nregs[first_regno] - [GET_MODE (XEXP (link, 0))]); - - for (i = first_regno; i < last_regno; i++) - SET_HARD_REG_BIT (pending_dead_regs, i); - } + add_to_hard_reg_set (&pending_dead_regs, + GET_MODE (XEXP (link, 0)), + REGNO (XEXP (link, 0))); note_stores (PATTERN (real_insn), update_live_status, NULL); @@ -1075,16 +1048,9 @@ mark_target_live_regs (rtx insns, rtx target, struct resources *res) if (REG_NOTE_KIND (link) == REG_UNUSED && REG_P (XEXP (link, 0)) && REGNO (XEXP (link, 0)) < FIRST_PSEUDO_REGISTER) - { - unsigned int first_regno = REGNO (XEXP (link, 0)); - unsigned int last_regno - = (first_regno - + hard_regno_nregs[first_regno] - [GET_MODE (XEXP (link, 0))]); - - for (i = first_regno; i < last_regno; i++) - CLEAR_HARD_REG_BIT (current_live_regs, i); - } + remove_from_hard_reg_set (¤t_live_regs, + GET_MODE (XEXP (link, 0)), + REGNO (XEXP (link, 0))); } else if (LABEL_P (real_insn)) diff --git a/gcc/rtlanal.c b/gcc/rtlanal.c index ce7018b..6a06f30 100644 --- a/gcc/rtlanal.c +++ b/gcc/rtlanal.c @@ -1233,10 +1233,7 @@ refers_to_regno_p (unsigned int regno, unsigned int endregno, rtx x, && regno >= FIRST_VIRTUAL_REGISTER && regno <= LAST_VIRTUAL_REGISTER) return 1; - return (endregno > x_regno - && regno < x_regno + (x_regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[x_regno][GET_MODE (x)] - : 1)); + return endregno > x_regno && regno < END_REGNO (x); case SUBREG: /* If this is a SUBREG of a hard reg, we can see exactly which @@ -1343,8 +1340,7 @@ reg_overlap_mentioned_p (rtx x, rtx in) case REG: regno = REGNO (x); - endregno = regno + (regno < FIRST_PSEUDO_REGISTER - ? hard_regno_nregs[regno][GET_MODE (x)] : 1); + endregno = END_REGNO (x); do_reg: return refers_to_regno_p (regno, endregno, in, (rtx*) 0); @@ -1551,7 +1547,7 @@ note_uses (rtx *pbody, void (*fun) (rtx *, void *), void *data) int dead_or_set_p (rtx insn, rtx x) { - unsigned int regno, last_regno; + unsigned int regno, end_regno; unsigned int i; /* Can't use cc0_rtx below since this file is used by genattrtab.c. */ @@ -1561,10 +1557,8 @@ dead_or_set_p (rtx insn, rtx x) gcc_assert (REG_P (x)); regno = REGNO (x); - last_regno = (regno >= FIRST_PSEUDO_REGISTER ? regno - : regno + hard_regno_nregs[regno][GET_MODE (x)] - 1); - - for (i = regno; i <= last_regno; i++) + end_regno = END_REGNO (x); + for (i = regno; i < end_regno; i++) if (! dead_or_set_regno_p (insn, i)) return 0; @@ -1591,8 +1585,7 @@ covers_regno_no_parallel_p (rtx dest, unsigned int test_regno) return false; regno = REGNO (dest); - endregno = (regno >= FIRST_PSEUDO_REGISTER ? regno + 1 - : regno + hard_regno_nregs[regno][GET_MODE (dest)]); + endregno = END_REGNO (dest); return (test_regno >= regno && test_regno < endregno); } @@ -1713,11 +1706,7 @@ find_regno_note (rtx insn, enum reg_note kind, unsigned int regno) problem here. */ && REG_P (XEXP (link, 0)) && REGNO (XEXP (link, 0)) <= regno - && ((REGNO (XEXP (link, 0)) - + (REGNO (XEXP (link, 0)) >= FIRST_PSEUDO_REGISTER ? 1 - : hard_regno_nregs[REGNO (XEXP (link, 0))] - [GET_MODE (XEXP (link, 0))])) - > regno)) + && END_REGNO (XEXP (link, 0)) > regno) return link; return 0; } @@ -1807,8 +1796,7 @@ find_reg_fusage (rtx insn, enum rtx_code code, rtx datum) if (regno < FIRST_PSEUDO_REGISTER) { - unsigned int end_regno - = regno + hard_regno_nregs[regno][GET_MODE (datum)]; + unsigned int end_regno = END_HARD_REGNO (datum); unsigned int i; for (i = regno; i < end_regno; i++) @@ -1837,13 +1825,12 @@ find_regno_fusage (rtx insn, enum rtx_code code, unsigned int regno) for (link = CALL_INSN_FUNCTION_USAGE (insn); link; link = XEXP (link, 1)) { - unsigned int regnote; rtx op, reg; if (GET_CODE (op = XEXP (link, 0)) == code && REG_P (reg = XEXP (op, 0)) - && (regnote = REGNO (reg)) <= regno - && regnote + hard_regno_nregs[regnote][GET_MODE (reg)] > regno) + && REGNO (reg) <= regno + && END_HARD_REGNO (reg) > regno) return 1; } @@ -575,14 +575,9 @@ decl_overlaps_hard_reg_set_p (tree *declp, int *walk_subtrees ATTRIBUTE_UNUSED, && REGNO (DECL_RTL (decl)) < FIRST_PSEUDO_REGISTER) { rtx reg = DECL_RTL (decl); - unsigned int regno; - - for (regno = REGNO (reg); - regno < (REGNO (reg) - + hard_regno_nregs[REGNO (reg)][GET_MODE (reg)]); - regno++) - if (TEST_HARD_REG_BIT (*regs, regno)) - return decl; + + if (overlaps_hard_reg_set_p (*regs, GET_MODE (reg), REGNO (reg))) + return decl; } walk_subtrees = 0; } diff --git a/gcc/var-tracking.c b/gcc/var-tracking.c index d9f21b5..94a025a 100644 --- a/gcc/var-tracking.c +++ b/gcc/var-tracking.c @@ -2389,8 +2389,7 @@ emit_note_insn_var_location (void **varp, void *data) if (REG_P (loc[n_var_parts]) && hard_regno_nregs[REGNO (loc[n_var_parts])][mode] * 2 == hard_regno_nregs[REGNO (loc[n_var_parts])][wider_mode] - && REGNO (loc[n_var_parts]) - + hard_regno_nregs[REGNO (loc[n_var_parts])][mode] + && end_hard_regno (mode, REGNO (loc[n_var_parts])) == REGNO (loc2)) { if (! WORDS_BIG_ENDIAN && ! BYTES_BIG_ENDIAN) |