diff options
| author | aoliva <aoliva@138bc75d-0d04-0410-961f-82ee72b054a4> | 2001-01-07 02:26:51 +0000 | 
|---|---|---|
| committer | aoliva <aoliva@138bc75d-0d04-0410-961f-82ee72b054a4> | 2001-01-07 02:26:51 +0000 | 
| commit | d3ff0f753948e4e595c6cf3d77ac1b05c655b464 (patch) | |
| tree | 17de3bb34420626f8eab111aee34a18e3a1f275f /gcc | |
| parent | 0351a03252ba852c678fade3693ba70f6a75cdf4 (diff) | |
| download | ppe42-gcc-d3ff0f753948e4e595c6cf3d77ac1b05c655b464.tar.gz ppe42-gcc-d3ff0f753948e4e595c6cf3d77ac1b05c655b464.zip | |
* reload.c (subst_reloads): Take INSN argument.  When
replacing a LABEL_REF in a JUMP_INSN, add a REG_LABEL note.
* reload.h (subst_reloads): Adjust prototype.
* reload1.c (reload_as_needed): Pass INSN to subst_reloads.
* jump.c (mark_all_labels): Canonicalize any REG_LABEL notes
present in JUMP_INSNs and copy them to JUMP_LABEL.
* flow.c (find_label_refs, find_basic_blocks_1): Skip
JUMP_INSNs and insns with REG_LABELs that are followed by
JUMP_INSNs with the same REG_LABEL.
* sched-rgn.c (is_cfg_nonregular): Likewise.
* rtlanal.c (computed_jump_p): Make it false if a REG_LABEL
note is available.
* unroll.c (unroll_loop): Look for REG_LABEL notes in
JUMP_INSNs too.
* rtl.texi (REG_LABEL): Document usage in JUMP_INSNs.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@38755 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc')
| -rw-r--r-- | gcc/ChangeLog | 18 | ||||
| -rw-r--r-- | gcc/flow.c | 24 | ||||
| -rw-r--r-- | gcc/jump.c | 18 | ||||
| -rw-r--r-- | gcc/reload.c | 12 | ||||
| -rw-r--r-- | gcc/reload.h | 4 | ||||
| -rw-r--r-- | gcc/reload1.c | 2 | ||||
| -rw-r--r-- | gcc/rtl.texi | 9 | ||||
| -rw-r--r-- | gcc/rtlanal.c | 6 | ||||
| -rw-r--r-- | gcc/sched-rgn.c | 17 | ||||
| -rw-r--r-- | gcc/unroll.c | 4 | 
10 files changed, 90 insertions, 24 deletions
| diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 2ae2ced5039..e912ed00b91 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,21 @@ +2001-01-07  Alexandre Oliva  <aoliva@redhat.com> + +	* reload.c (subst_reloads): Take INSN argument.  When +	replacing a LABEL_REF in a JUMP_INSN, add a REG_LABEL note. +	* reload.h (subst_reloads): Adjust prototype. +	* reload1.c (reload_as_needed): Pass INSN to subst_reloads. +	* jump.c (mark_all_labels): Canonicalize any REG_LABEL notes +	present in JUMP_INSNs and copy them to JUMP_LABEL. +	* flow.c (find_label_refs, find_basic_blocks_1): Skip +	JUMP_INSNs and insns with REG_LABELs that are followed by +	JUMP_INSNs with the same REG_LABEL. +	* sched-rgn.c (is_cfg_nonregular): Likewise. +	* rtlanal.c (computed_jump_p): Make it false if a REG_LABEL +	note is available. +	* unroll.c (unroll_loop): Look for REG_LABEL notes in +	JUMP_INSNs too. +	* rtl.texi (REG_LABEL): Document usage in JUMP_INSNs. +  2001-01-06  Richard Henderson  <rth@redhat.com>  	* loop.c (scan_loop): Use xcalloc for the regs array. diff --git a/gcc/flow.c b/gcc/flow.c index 5eaf116238f..a53043dc534 100644 --- a/gcc/flow.c +++ b/gcc/flow.c @@ -640,7 +640,7 @@ find_label_refs (f, lvl)    rtx insn;    for (insn = f; insn; insn = NEXT_INSN (insn)) -    if (INSN_P (insn)) +    if (INSN_P (insn) && GET_CODE (insn) != JUMP_INSN)        {  	rtx note; @@ -651,7 +651,10 @@ find_label_refs (f, lvl)  	   as this would be a part of the tablejump setup code.  	   Make a special exception for the eh_return_stub_label, which -	   we know isn't part of any otherwise visible control flow.  */ +	   we know isn't part of any otherwise visible control flow. + +	   Make a special exception to registers loaded with label +	   values just before jump insns that use them.  */  	for (note = REG_NOTES (insn); note; note = XEXP (note, 1))  	  if (REG_NOTE_KIND (note) == REG_LABEL) @@ -667,6 +670,9 @@ find_label_refs (f, lvl)  		;  	      else if (GET_CODE (lab) == NOTE)  		; +	      else if (GET_CODE (NEXT_INSN (insn)) == JUMP_INSN +		       && find_reg_note (NEXT_INSN (insn), REG_LABEL, lab)) +		;  	      else  		lvl = alloc_EXPR_LIST (0, XEXP (note, 0), lvl);  	    } @@ -862,18 +868,21 @@ find_basic_blocks_1 (f)  	  break;  	} -      if (GET_RTX_CLASS (code) == 'i') +      if (GET_RTX_CLASS (code) == 'i' +	  && GET_CODE (insn) != JUMP_INSN)  	{  	  rtx note; -	  /* Make a list of all labels referred to other than by jumps -	     (which just don't have the REG_LABEL notes). +	  /* Make a list of all labels referred to other than by jumps.  	     Make a special exception for labels followed by an ADDR*VEC,  	     as this would be a part of the tablejump setup code.  	     Make a special exception for the eh_return_stub_label, which -	     we know isn't part of any otherwise visible control flow.  */ +	     we know isn't part of any otherwise visible control flow. + +	     Make a special exception to registers loaded with label +	     values just before jump insns that use them.  */  	  for (note = REG_NOTES (insn); note; note = XEXP (note, 1))  	    if (REG_NOTE_KIND (note) == REG_LABEL) @@ -889,6 +898,9 @@ find_basic_blocks_1 (f)  		  ;  		else if (GET_CODE (lab) == NOTE)  		  ; +		else if (GET_CODE (NEXT_INSN (insn)) == JUMP_INSN +			 && find_reg_note (NEXT_INSN (insn), REG_LABEL, lab)) +		  ;  		else  		  lvl = alloc_EXPR_LIST (0, XEXP (note, 0), lvl);  	      } diff --git a/gcc/jump.c b/gcc/jump.c index 1c6c3a633d6..032172d3907 100644 --- a/gcc/jump.c +++ b/gcc/jump.c @@ -863,6 +863,24 @@ mark_all_labels (f, cross_jump)  	mark_jump_label (PATTERN (insn), insn, cross_jump, 0);  	if (! INSN_DELETED_P (insn) && GET_CODE (insn) == JUMP_INSN)  	  { +	    /* When we know the LABEL_REF contained in a REG used in +	       an indirect jump, we'll have a REG_LABEL note so that +	       flow can tell where it's going.  */ +	    if (JUMP_LABEL (insn) == 0) +	      { +		rtx label_note = find_reg_note (insn, REG_LABEL, NULL_RTX); +		if (label_note) +		  { +		    /* But a LABEL_REF around the REG_LABEL note, so +		       that we can canonicalize it.  */ +		    rtx label_ref = gen_rtx_LABEL_REF (VOIDmode, +						       XEXP (label_note, 0)); + +		    mark_jump_label (label_ref, insn, cross_jump, 0); +		    XEXP (label_note, 0) = XEXP (label_ref, 0); +		    JUMP_LABEL (insn) = XEXP (label_note, 0); +		  } +	      }  	    if (JUMP_LABEL (insn) != 0 && simplejump_p (insn))  	      {  		jump_chain[INSN_UID (insn)] diff --git a/gcc/reload.c b/gcc/reload.c index 7b9b669e09e..11e33f05fc8 100644 --- a/gcc/reload.c +++ b/gcc/reload.c @@ -5679,7 +5679,8 @@ find_reloads_subreg_address (x, force_replace, opnum, type,     Return the rtx that X translates into; usually X, but modified.  */  void -subst_reloads () +subst_reloads (insn) +     rtx insn;  {    register int i; @@ -5689,6 +5690,15 @@ subst_reloads ()        register rtx reloadreg = rld[r->what].reg_rtx;        if (reloadreg)  	{ +	  /* If we're replacing a LABEL_REF with a register, add a +	     REG_LABEL note to indicate to flow which label this +	     register refers to.  */ +	  if (GET_CODE (*r->where) == LABEL_REF +	      && GET_CODE (insn) == JUMP_INSN) +	    REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_LABEL, +						  XEXP (*r->where, 0), +						  REG_NOTES (insn)); +  	  /* Encapsulate RELOADREG so its machine mode matches what  	     used to be there.  Note that gen_lowpart_common will  	     do the wrong thing if RELOADREG is multi-word.  RELOADREG diff --git a/gcc/reload.h b/gcc/reload.h index 7841c7ad7d1..b604184a529 100644 --- a/gcc/reload.h +++ b/gcc/reload.h @@ -1,6 +1,6 @@  /* Communication between reload.c and reload1.c.     Copyright (C) 1987, 1991, 1992, 1993, 1994, 1995, 1997, 1998, -   1999, 2000 Free Software Foundation, Inc. +   1999, 2000, 2001 Free Software Foundation, Inc.  This file is part of GNU CC. @@ -302,7 +302,7 @@ extern rtx form_sum PARAMS ((rtx, rtx));  /* Substitute into the current INSN the registers into which we have reloaded     the things that need reloading.  */ -extern void subst_reloads PARAMS ((void)); +extern void subst_reloads PARAMS ((rtx));  /* Make a copy of any replacements being done into X and move those copies     to locations in Y, a copy of X.  We only look at the highest level of diff --git a/gcc/reload1.c b/gcc/reload1.c index 3a3dab0e7d4..783c8dc9beb 100644 --- a/gcc/reload1.c +++ b/gcc/reload1.c @@ -3830,7 +3830,7 @@ reload_as_needed (live_known)  		 into the insn's body (or perhaps into the bodies of other  		 load and store insn that we just made for reloading  		 and that we moved the structure into).  */ -	      subst_reloads (); +	      subst_reloads (insn);  	      /* If this was an ASM, make sure that all the reload insns  		 we have generated are valid.  If not, give an error diff --git a/gcc/rtl.texi b/gcc/rtl.texi index 15911cd7ce8..0e9d8c48652 100644 --- a/gcc/rtl.texi +++ b/gcc/rtl.texi @@ -1,4 +1,5 @@ -@c Copyright (C) 1988, 89, 92, 94, 97, 1998, 1999, 2000 Free Software Foundation, Inc. +@c Copyright (C) 1988, 1989, 1992, 1994, 1997, 1998, 1999, 2000, 2001 +@c Free Software Foundation, Inc.  @c This is part of the GCC manual.  @c For copying conditions, see the file gcc.texi. @@ -2752,8 +2753,10 @@ last insns, respectively.  @findex REG_LABEL  @item REG_LABEL  This insn uses @var{op}, a @code{code_label}, but is not a -@code{jump_insn}.  The presence of this note allows jump optimization to -be aware that @var{op} is, in fact, being used. +@code{jump_insn}, or it is a @code{jump_insn} that required the label to +be held in a register.  The presence of this note allows jump +optimization to be aware that @var{op} is, in fact, being used, and flow +optimization to build an accurate flow graph.  @end table  The following notes describe attributes of outputs of an insn: diff --git a/gcc/rtlanal.c b/gcc/rtlanal.c index 67c5319dfbf..b0fbcf31063 100644 --- a/gcc/rtlanal.c +++ b/gcc/rtlanal.c @@ -1,6 +1,6 @@  /* Analyze RTL for C-Compiler     Copyright (C) 1987, 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1998, -   1999, 2000 Free Software Foundation, Inc. +   1999, 2000, 2001 Free Software Foundation, Inc.  This file is part of GNU CC. @@ -2285,7 +2285,9 @@ computed_jump_p (insn)      {        rtx pat = PATTERN (insn); -      if (GET_CODE (pat) == PARALLEL) +      if (find_reg_note (insn, REG_LABEL, NULL_RTX)) +	return 0; +      else if (GET_CODE (pat) == PARALLEL)  	{  	  int len = XVECLEN (pat, 0);  	  int has_use_labelref = 0; diff --git a/gcc/sched-rgn.c b/gcc/sched-rgn.c index db4cc877b36..c1c215a1ea9 100644 --- a/gcc/sched-rgn.c +++ b/gcc/sched-rgn.c @@ -1,6 +1,6 @@  /* Instruction scheduling pass.     Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, -   1999, 2000 Free Software Foundation, Inc. +   1999, 2000, 2001 Free Software Foundation, Inc.     Contributed by Michael Tiemann (tiemann@cygnus.com) Enhanced by,     and currently maintained by, Jim Wilson (wilson@cygnus.com) @@ -349,13 +349,16 @@ is_cfg_nonregular ()      for (insn = BLOCK_HEAD (b);; insn = NEXT_INSN (insn))        {  	code = GET_CODE (insn); -	if (GET_RTX_CLASS (code) == 'i') +	if (GET_RTX_CLASS (code) == 'i' && code != JUMP_INSN)  	  { -	    rtx note; - -	    for (note = REG_NOTES (insn); note; note = XEXP (note, 1)) -	      if (REG_NOTE_KIND (note) == REG_LABEL) -		return 1; +	    rtx note = find_reg_note (REG_NOTES (insn), REG_LABEL, NULL_RTX); + +	    if (note +		&& ! (GET_CODE (NEXT_INSN (insn)) == JUMP_INSN +		      && find_reg_note (REG_NOTES (NEXT_INSN (insn)), +					REG_LABEL, +					XEXP (note, 0)))) +	      return 1;  	  }  	if (insn == BLOCK_END (b)) diff --git a/gcc/unroll.c b/gcc/unroll.c index 0b4a89bfd28..bdd6cb4e781 100644 --- a/gcc/unroll.c +++ b/gcc/unroll.c @@ -1,5 +1,5 @@  /* Try to unroll loops, and split induction variables. -   Copyright (C) 1992, 1993, 1994, 1995, 1997, 1998, 1999, 2000 +   Copyright (C) 1992, 1993, 1994, 1995, 1997, 1998, 1999, 2000, 2001     Free Software Foundation, Inc.     Contributed by James E. Wilson, Cygnus Support/UC Berkeley. @@ -768,7 +768,7 @@ unroll_loop (loop, insn_count, end_insert_before, strength_reduce_p)  		}  	    }  	} -      else if ((note = find_reg_note (insn, REG_LABEL, NULL_RTX))) +      if ((note = find_reg_note (insn, REG_LABEL, NULL_RTX)))  	set_label_in_map (map, CODE_LABEL_NUMBER (XEXP (note, 0)),  			  XEXP (note, 0));      } | 

