[PATCH 0/2] Convert s390 to atomic optabs, v2

Richard Henderson rth@redhat.com
Wed Aug 1 23:23:00 GMT 2012


Please try this as a followup to the previous two patches.
That should clean up the mistake with the insv change.


r~
-------------- next part --------------
commit 6b07a31943bcbca2a4f6fae707cf3d7ae283d4dc
Author: Richard Henderson <rth@redhat.com>
Date:   Wed Aug 1 16:10:37 2012 -0700

    fixup insv

diff --git a/gcc/config/s390/s390.c b/gcc/config/s390/s390.c
index 8259e2b..35c7fb5 100644
--- a/gcc/config/s390/s390.c
+++ b/gcc/config/s390/s390.c
@@ -4551,7 +4551,8 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
   int bitsize = INTVAL (op1);
   int bitpos = INTVAL (op2);
   enum machine_mode mode = GET_MODE (dest);
-  enum machine_mode smode = smallest_mode_for_size (bitsize, MODE_INT);
+  enum machine_mode smode;
+  int smode_bsize, mode_bsize;
   rtx op, clobber;
 
   /* Generate INSERT IMMEDIATE (IILL et al).  */
@@ -4587,6 +4588,10 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
       return true;
     }
 
+  smode = smallest_mode_for_size (bitsize, MODE_INT);
+  smode_bsize = GET_MODE_BITSIZE (smode);
+  mode_bsize = GET_MODE_BITSIZE (mode);
+
   /* Generate STORE CHARACTERS UNDER MASK (STCM et al).  */
   if (bitpos == 0
       && (bitsize % BITS_PER_UNIT) == 0
@@ -4595,7 +4600,7 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
 	  || const_int_operand (src, VOIDmode)))
     {
       /* Emit standard pattern if possible.  */
-      if (GET_MODE_BITSIZE (smode) == bitsize)
+      if (smode_bsize == bitsize)
 	{
 	  emit_move_insn (adjust_address (dest, smode, 0),
 			  gen_lowpart (smode, src));
@@ -4608,7 +4613,7 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
 	  int size = bitsize / BITS_PER_UNIT;
 	  rtx src_mem = adjust_address (force_const_mem (word_mode, src),
 					BLKmode,
-					GET_MODE_SIZE (word_mode) - size);
+					UNITS_PER_WORD - size);
 
 	  dest = adjust_address (dest, BLKmode, 0);
 	  set_mem_size (dest, size);
@@ -4619,22 +4624,22 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
       /* (set (ze (mem)) (reg)).  */
       else if (register_operand (src, word_mode))
 	{
-	  if (bitsize <= GET_MODE_BITSIZE (SImode))
+	  if (bitsize <= 32)
 	    emit_move_insn (gen_rtx_ZERO_EXTRACT (word_mode, dest, op1,
 						  const0_rtx), src);
 	  else
 	    {
 	      /* Emit st,stcmh sequence.  */
-	      int stcmh_width = bitsize - GET_MODE_BITSIZE (SImode);
+	      int stcmh_width = bitsize - 32;
 	      int size = stcmh_width / BITS_PER_UNIT;
 
 	      emit_move_insn (adjust_address (dest, SImode, size),
 			      gen_lowpart (SImode, src));
 	      set_mem_size (dest, size);
-	      emit_move_insn (gen_rtx_ZERO_EXTRACT (word_mode, dest, GEN_INT
-						    (stcmh_width), const0_rtx),
-			      gen_rtx_LSHIFTRT (word_mode, src, GEN_INT
-						(GET_MODE_BITSIZE (SImode))));
+	      emit_move_insn (gen_rtx_ZERO_EXTRACT (word_mode, dest,
+						    GEN_INT (stcmh_width),
+						    const0_rtx),
+			      gen_rtx_LSHIFTRT (word_mode, src, GEN_INT (32)));
 	    }
 	  return true;
 	}
@@ -4649,7 +4654,7 @@ s390_expand_insv (rtx dest, rtx op1, rtx op2, rtx src)
       && register_operand (dest, mode))
     {
       /* Emit a strict_low_part pattern if possible.  */
-      if (bitpos == 0 && GET_MODE_BITSIZE (smode) == bitsize)
+      if (smode_bsize == bitsize && bitpos == mode_bsize - smode_bsize)
 	{
 	  op = gen_rtx_STRICT_LOW_PART (VOIDmode, gen_lowpart (smode, dest));
 	  op = gen_rtx_SET (VOIDmode, op, gen_lowpart (smode, src));
@@ -4728,7 +4733,12 @@ init_alignment_context (struct alignment_context *ac, rtx mem,
   ac->aligned = (MEM_ALIGN (mem) >= GET_MODE_BITSIZE (SImode));
 
   if (ac->aligned)
-    ac->memsi = adjust_address (mem, SImode, 0); /* Memory is aligned.  */
+    {
+      ac->memsi = adjust_address (mem, SImode, 0); /* Memory is aligned.  */
+      ac->shift = const0_rtx;
+      ac->modemask = GEN_INT (GET_MODE_MASK (mode));
+      ac->modemaski = GEN_INT (~GET_MODE_MASK (mode));
+    }
   else
     {
       /* Alignment is unknown.  */
@@ -4755,15 +4765,17 @@ init_alignment_context (struct alignment_context *ac, rtx mem,
       ac->shift = expand_simple_binop (SImode, MINUS, ac->shift, byteoffset,
 				      NULL_RTX, 1, OPTAB_DIRECT);
 
+      /* Shift is the byte count, but we need the bitcount.  */
+      ac->shift = expand_simple_binop (SImode, ASHIFT, ac->shift, GEN_INT (3),
+				       NULL_RTX, 1, OPTAB_DIRECT);
+
+      /* Calculate masks.  */
+      ac->modemask = expand_simple_binop (SImode, ASHIFT,
+					  GEN_INT (GET_MODE_MASK (mode)),
+					  ac->shift, NULL_RTX, 1, OPTAB_DIRECT);
+      ac->modemaski = expand_simple_unop (SImode, NOT, ac->modemask,
+					  NULL_RTX, 1);
     }
-  /* Shift is the byte count, but we need the bitcount.  */
-  ac->shift = expand_simple_binop (SImode, MULT, ac->shift, GEN_INT (BITS_PER_UNIT),
-				  NULL_RTX, 1, OPTAB_DIRECT);
-  /* Calculate masks.  */
-  ac->modemask = expand_simple_binop (SImode, ASHIFT,
-				     GEN_INT (GET_MODE_MASK (mode)), ac->shift,
-				     NULL_RTX, 1, OPTAB_DIRECT);
-  ac->modemaski = expand_simple_unop (SImode, NOT, ac->modemask, NULL_RTX, 1);
 }
 
 /* A subroutine of s390_expand_cs_hqi.  Insert INS into VAL.  If possible,
@@ -4781,7 +4793,7 @@ s390_two_part_insv (struct alignment_context *ac, rtx *seq1, rtx *seq2,
       start_sequence ();
       tmp = copy_to_mode_reg (SImode, val);
       if (s390_expand_insv (tmp, GEN_INT (GET_MODE_BITSIZE (mode)),
-			    const0_rtx, ins))
+			    GEN_INT (32 - GET_MODE_BITSIZE (mode)), ins))
 	{
 	  *seq1 = NULL;
 	  *seq2 = get_insns ();


More information about the Gcc-patches mailing list