This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

One more optimize_mode_switching() problem


If the last insn of a function is a DFmode store, and prologue and
epilogue must run in single mode, the mode switching would be inserted
before the store, because there was not NOTE_INSN_BASIC_BLOCK after it
that ptr->insn_ptr could be pointed to.  This patch fixes this, by
arranging for the mode set to be emitted after the insn, unless it's a
jump insn.  I believe there would be some ambiguity in case jump insns
required particular modes, but since SH is the only current user of
this feature, and jumps don't require any particular modes, this is
probably ok for now.  Ok to install if it passes regression tests on
sh-elf?

Index: gcc/ChangeLog
from  Alexandre Oliva  <aoliva@redhat.com>
	* lcm.c (optimize_mode_switching): Emit mode switching after last
	insn of a function, unless it's a jump.

2001-02-07  Alexandre Oliva  <aoliva@redhat.com>

Index: gcc/lcm.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/lcm.c,v
retrieving revision 1.22
diff -u -p -r1.22 lcm.c
--- gcc/lcm.c 2001/02/07 17:44:47 1.22
+++ gcc/lcm.c 2001/02/07 17:45:40
@@ -1273,9 +1273,12 @@ optimize_mode_switching (file)
 		  mode_set = gen_sequence ();
 		  end_sequence ();
 
-		  if (GET_CODE (ptr->insn_ptr) == NOTE
-		      && (NOTE_LINE_NUMBER (ptr->insn_ptr)
-			  == NOTE_INSN_BASIC_BLOCK))
+		  if ((GET_CODE (ptr->insn_ptr) == NOTE
+		       && (NOTE_LINE_NUMBER (ptr->insn_ptr)
+			   == NOTE_INSN_BASIC_BLOCK))
+		      || (GET_CODE (ptr->insn_ptr) != JUMP_INSN
+			  && ptr->bbnum == n_basic_blocks - 1
+			  && ptr->insn_ptr == BLOCK_END (ptr->bbnum)))
 		    emit_block_insn_after (mode_set, ptr->insn_ptr,
     		                           BASIC_BLOCK (ptr->bbnum));
 		  else

In the future, we may want to arrange for a end-of-function block to
be introduced, in which we could add mode switches.  Otherwise, a
function like this: `void f(double i) { while (--i); }' compiles into
something like:

enter double mode
branch 1f
0:
enter double mode
1:
decrement i
test i == 0.0
enter single mode
branch 0 if false
return

If we had an end-of-function basic block, we'd probably have
generated:

enter double mode
0:
decrement i
test i == 0.0
branch 0 if false
enter single mode
return

-- 
Alexandre Oliva   Enjoy Guarana', see http://www.ic.unicamp.br/~oliva/
Red Hat GCC Developer                  aoliva@{cygnus.com, redhat.com}
CS PhD student at IC-Unicamp        oliva@{lsd.ic.unicamp.br, gnu.org}
Free Software Evangelist    *Please* write to mailing lists, not to me

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]