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]

[patch] h8300.md: Improve andsi3.


Hi,

Attached is a patch to improve andsi3 in the h8300 port.  I basically
rewrote it to improve the code quality.

I tested with newlib and found a number of occurences of the following
kinds of differences.  (I manually converted literals to hex decimal
for your convenience.  With my patch applied, gcc still generates
literals in decimal.)

On H8/300H and H8/S, and.l is replaced with and.w if AND affects only
the upper word.  The insn length is down to 4 bytes from 6 bytes.

-	and.l	#0x7fffffff,er4
+	and.w	#0x7fff,e4

On H8/300H and H8/S, a sequence of two byte-wide ANDs is replaced with
word-wide AND.  Despite the appearance, there is no win of any kind
other than better readability.

-	and	#0x3f,r5l
-	and	#0xfd,r5h
+	and.w	#0xfd3f,r5

On H8/300H and H8/S, masking off the upper half becomes more
efficient.  The insn length is down to 2 bytes from 4 bytes.

-	and.l	#0xffff,er0
+	sub.w	e0,e0

On any H8, the order of bytes ANDed within a 32-bit register may
change, but this is OK.

-	sub.w	r4,r4
 	and	#0x03,r5l
 	and	#0x00,r5h
+	sub.w	r4,r4

In any case, the original gcc has "clobber" as far as cc0 is
concerned, which I still keep it that way.  Therefore, there is no
code increase due to new test insns that aren't originally there.

OK to apply?  (Even though the patch is generated against gcc-3.0, it
is really for CVS HEAD unless it's OK to apply it to gcc-3.0. :-)

Thanks,

Kazu Hirata

2001-02-18  Kazu Hirata  <kazu@hxi.com>

	* config/h8300/h8300.md (andsi): Rewrite to improve the code
	quality.

Index: h8300.md
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/h8300/h8300.md,v
retrieving revision 1.23.4.1
diff -c -3 -p -r1.23.4.1 h8300.md
*** h8300.md	2001/02/19 02:23:25	1.23.4.1
--- h8300.md	2001/02/19 03:10:31
***************
*** 993,1040 ****
    ""
    "*
  {
!   if (GET_CODE (operands[2]) == CONST_INT)
!     {
!       int i = INTVAL (operands[2]);
!       int upper_cleared, lower_cleared;
! 
!       /* The h8300h can't do byte-wise operations on the
! 	 upper 16bits of 32bit registers.  However, if
! 	 those bits aren't going to change, or they're
! 	 going to be zero'd out, then we can work on the
! 	 low-order bits.  */
!       if ((TARGET_H8300H || TARGET_H8300S)
! 	  && ((i & 0xffff0000) != 0xffff0000
! 	      || (i & 0xffff0000) == 0x00000000))
!         return \"and.l	%S2,%S0\";
  
!       lower_cleared = 0;
!       if ((i & 0x0000ffff) == 0x00000000)
! 	{
! 	  output_asm_insn (\"sub.w	%f0,%f0\", operands);
! 	  lower_cleared = 1;
! 	}
  
!       upper_cleared = 0;
!       if ((i & 0xffff0000) == 0x00000000)
! 	{
! 	  output_asm_insn (\"sub.w	%e0,%e0\", operands);
! 	  upper_cleared = 1;
! 	}
  
!       if ((i & 0x000000ff) != 0x000000ff && !lower_cleared)
! 	output_asm_insn (\"and	%w2,%w0\", operands);
!       if ((i & 0x0000ff00) != 0x0000ff00 && !lower_cleared)
! 	output_asm_insn (\"and	%x2,%x0\", operands);
!       if ((i & 0x00ff0000) != 0x00ff0000 && !upper_cleared)
! 	output_asm_insn (\"and	%y2,%y0\", operands);
!       if ((i & 0xff000000) != 0xff000000 && !upper_cleared)
! 	output_asm_insn (\"and	%z2,%z0\", operands);
!       return \"\";
      }
!   if (TARGET_H8300H || TARGET_H8300S)
!     return \"and.l	%S2,%S0\";
!   return \"and	%w2,%w0\;and	%x2,%x0\;and	%y2,%y0\;and	%z2,%z0\";
  }"
    [(set_attr "length" "8")
     (set_attr "cc" "clobber")])
--- 993,1040 ----
    ""
    "*
  {
!   /* Pretend that every byte is affected if we are ANDing with a
!      non-constant.  */
!   int i = ((GET_CODE (operands[2]) == CONST_INT)
! 	   ? INTVAL (operands[2]) : 0x11111111);
  
!   /* Are both upper and lower words affected?  */
!   if ((TARGET_H8300H || TARGET_H8300S)
!       && ((i & 0xffff0000) != 0xffff0000)
!       && ((i & 0x0000ffff) != 0x0000ffff))
!     return \"and.l\\t%S2,%S0\";
  
!   /* Is the lower word is cleared?  */
!   if ((i & 0x0000ffff) == 0x00000000)
!     output_asm_insn (\"sub.w\\t%f0,%f0\", operands);
!   /* Are both bytes in the lower word affected?  */
!   else if ((TARGET_H8300H || TARGET_H8300S)
! 	   && ((i & 0x000000ff) != 0x000000ff)
! 	   && ((i & 0x0000ff00) != 0x0000ff00))
!     output_asm_insn (\"and.w\\t%f2,%f0\", operands);
!   else
!     {
!       if ((i & 0x000000ff) != 0x000000ff)
! 	output_asm_insn (\"and\\t%w2,%w0\", operands);
!       if ((i & 0x0000ff00) != 0x0000ff00)
! 	output_asm_insn (\"and\\t%x2,%x0\", operands);
!     }
  
!   /* Is the upper word is cleared?  */
!   if ((i & 0xffff0000) == 0x00000000)
!     output_asm_insn (\"sub.w\\t%e0,%e0\", operands);
!   /* Is the upper word affected?  */
!   else if ((TARGET_H8300H || TARGET_H8300S)
! 	   && ((i & 0xffff0000) != 0xffff0000))
!     output_asm_insn (\"and.w\\t%e2,%e0\", operands);
!   else
!     {
!       if ((i & 0x00ff0000) != 0x00ff0000)
! 	output_asm_insn (\"and\\t%y2,%y0\", operands);
!       if ((i & 0xff000000) != 0xff000000)
! 	output_asm_insn (\"and\\t%z2,%z0\", operands);
      }
!   return \"\";
  }"
    [(set_attr "length" "8")
     (set_attr "cc" "clobber")])


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