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]
Other format: [Raw text]

[committed] Second patch for PR target/33635 (mips-sgi-irix6.5 bootstrap)


FX reported that the first patch for this bug didn't fix the whole problem.
I'd forgotten to increase the REGISTER_MOVE_COST for FPR->FPR moves that
can no longer be done directly (they still had cost 2, which implies
that they don't need reloads).

Like mips_secondary_reload_class, mips_register_move_cost was rather
dusty, with many == checks that ought to be subset checks.  I couldn't
resist fixing that at the same time.  I ran CSiBE at -Os for
-mhard-float -Os, -msoft-float -Os and -mips16 -Os on mipsisa32-elf.
As expected, there were no differences for the first two.  Changing to
subset checks meant that the MIPS16 results were very slightly better
(by a whole 32 bytes).

I haven't tried to merge the GR <-> ACC, GR <-> FPR or GR <-> COP
cases because the costs of these moves aren't symmetric on some
processors.  It might be useful to add some processor-specific
tuning here in future.

FX tested the new FPR->FPR cost on mips-sgi-irix6.5 (thanks) and reports
that it fixes C + Fortran bootstrap.  I've regression-tested the patch
below on mipsisa32-elf.  Applied.

Richard


gcc/
	PR target/33635
	* config/mips/mips.c (mips_register_move_cost): Rewrite to use
	subset checks.  Make the cost of FPR -> FPR moves depend on
	mips_mode_ok_for_mov_fmt_p.

gcc/testsuite/
	PR target/33635
	* gcc.target/mips/pr33635-1.c: New test.

Index: gcc/config/mips/mips.c
===================================================================
*** gcc/config/mips/mips.c	2007-10-05 08:42:42.000000000 +0100
--- gcc/config/mips/mips.c	2007-10-05 09:07:00.000000000 +0100
*************** mips_init_libfuncs (void)
*** 10969,11037 ****
     we need to use.  This gets pretty messy, but it is feasible.  */
  
  int
! mips_register_move_cost (enum machine_mode mode ATTRIBUTE_UNUSED,
  			 enum reg_class to, enum reg_class from)
  {
!   if (from == M16_REGS && reg_class_subset_p (to, GENERAL_REGS))
!     return 2;
!   else if (from == M16_NA_REGS && reg_class_subset_p (to, GENERAL_REGS))
!     return 2;
!   else if (reg_class_subset_p (from, GENERAL_REGS))
      {
!       if (to == M16_REGS)
! 	return 2;
!       else if (to == M16_NA_REGS)
! 	return 2;
!       else if (reg_class_subset_p (to, GENERAL_REGS))
  	{
! 	  if (TARGET_MIPS16)
! 	    return 4;
! 	  else
  	    return 2;
! 	}
!       else if (to == FP_REGS)
! 	return 4;
!       else if (reg_class_subset_p (to, ACC_REGS))
! 	{
! 	  if (TARGET_MIPS16)
! 	    return 12;
! 	  else
! 	    return 6;
! 	}
!       else if (reg_class_subset_p (to, ALL_COP_REGS))
! 	{
! 	  return 5;
  	}
      }
!   else if (from == FP_REGS)
      {
        if (reg_class_subset_p (to, GENERAL_REGS))
- 	return 4;
-       else if (to == FP_REGS)
  	return 2;
!       else if (to == ST_REGS)
! 	return 8;
      }
!   else if (reg_class_subset_p (from, ACC_REGS))
      {
!       if (reg_class_subset_p (to, GENERAL_REGS))
! 	{
! 	  if (TARGET_MIPS16)
! 	    return 12;
! 	  else
! 	    return 6;
! 	}
      }
!   else if (from == ST_REGS && reg_class_subset_p (to, GENERAL_REGS))
!     return 4;
!   else if (reg_class_subset_p (from, ALL_COP_REGS))
      {
!       return 5;
      }
  
-   /* Fall through.
-      ??? What cases are these? Shouldn't we return 2 here?  */
- 
    return 12;
  }
  
--- 10969,11022 ----
     we need to use.  This gets pretty messy, but it is feasible.  */
  
  int
! mips_register_move_cost (enum machine_mode mode,
  			 enum reg_class to, enum reg_class from)
  {
!   if (TARGET_MIPS16)
      {
!       if (reg_class_subset_p (from, GENERAL_REGS)
! 	  && reg_class_subset_p (to, GENERAL_REGS))
  	{
! 	  if (reg_class_subset_p (from, M16_REGS)
! 	      || reg_class_subset_p (to, M16_REGS))
  	    return 2;
! 	  /* Two MOVEs.  */
! 	  return 4;
  	}
      }
!   else if (reg_class_subset_p (from, GENERAL_REGS))
      {
        if (reg_class_subset_p (to, GENERAL_REGS))
  	return 2;
!       if (reg_class_subset_p (to, FP_REGS))
! 	return 4;
!       if (reg_class_subset_p (to, ALL_COP_AND_GR_REGS))
! 	return 5;
!       if (reg_class_subset_p (to, ACC_REGS))
! 	return 6;
      }
!   else if (reg_class_subset_p (to, GENERAL_REGS))
      {
!       if (reg_class_subset_p (from, FP_REGS))
! 	return 4;
!       if (reg_class_subset_p (from, ST_REGS))
! 	/* LUI followed by MOVF.  */
! 	return 4;
!       if (reg_class_subset_p (from, ALL_COP_AND_GR_REGS))
! 	return 5;
!       if (reg_class_subset_p (from, ACC_REGS))
! 	return 6;
      }
!   else if (reg_class_subset_p (from, FP_REGS))
      {
!       if (reg_class_subset_p (to, FP_REGS)
! 	  && mips_mode_ok_for_mov_fmt_p (mode))
! 	return 4;
!       if (reg_class_subset_p (to, ST_REGS))
! 	/* An expensive sequence.  */
! 	return 8;
      }
  
    return 12;
  }
  
Index: gcc/testsuite/gcc.target/mips/pr33635-1.c
===================================================================
*** /dev/null	2007-10-04 21:37:48.552097000 +0100
--- gcc/testsuite/gcc.target/mips/pr33635-1.c	2007-10-05 09:03:30.000000000 +0100
***************
*** 0 ****
--- 1,13 ----
+ /* { dg-mips-options "-mabi=64 -O2" } */
+ 
+ NOMIPS16 long double __powitf2 (long double x, int m)
+ {
+   long double y = x;
+   while (m >>= 1)
+     {
+       x = x * x;
+       if (m % 2)
+         y = y * x;
+     }
+   return y;
+ }


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