public inbox for gcc@gcc.gnu.org
 help / color / mirror / Atom feed
* Sign extension by expr.c convert_move()
@ 2007-08-12 15:13 Rask Ingemann Lambertsen
  2007-08-13 21:50 ` Ian Lance Taylor
  0 siblings, 1 reply; 2+ messages in thread
From: Rask Ingemann Lambertsen @ 2007-08-12 15:13 UTC (permalink / raw)
  To: gcc

   In expr.c, convert_move() tries to synthesize sign extension in modes
larger than those directly supported by the target. There are two strategies
for generating the sign bit copies:

1) Compare with 0 and use "slt" if STORE_FLAG_VALUE == -1.
2) Use a signed right shift of one bit less than the operand width.

      /* Compute the value to put in each remaining word.  */
      if (unsignedp)
	fill_value = const0_rtx;
      else
	{
#ifdef HAVE_slt
	  if (HAVE_slt
	      && insn_data[(int) CODE_FOR_slt].operand[0].mode == word_mode
	      && STORE_FLAG_VALUE == -1)
	    {
	      emit_cmp_insn (lowfrom, const0_rtx, NE, NULL_RTX,
			     lowpart_mode, 0);
	      fill_value = gen_reg_rtx (word_mode);
	      emit_insn (gen_slt (fill_value));
	    }
	  else
#endif
	    {
	      fill_value
		= expand_shift (RSHIFT_EXPR, lowpart_mode, lowfrom,
				size_int (GET_MODE_BITSIZE (lowpart_mode) - 1),
				NULL_RTX, 0);
	      fill_value = convert_to_mode (word_mode, fill_value, 1);
	    }
	}

   My questions center around the first aproach:

1) Shouldn't it check that the comparison is directly supported by the
target rather than implemented by a library call? If not, how does it know
that it sets the codition codes? Also, several targets don't emit a
comparison instruction until they know how the result is used. Instead, they
save away the comparison operands. That will fail if the comparison is made
by a library call.
2) How does it handle failure of gen_slt?

   I've now hit a case (mulvsi3 on ia16) where it tries to sign extend from
SImode to DImode. It's just that cmpsi2 is implemented as a library call and
gen_slt() fails. Result: "Junk extended" arguments are passed to muldi3.

-- 
Rask Ingemann Lambertsen

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: Sign extension by expr.c convert_move()
  2007-08-12 15:13 Sign extension by expr.c convert_move() Rask Ingemann Lambertsen
@ 2007-08-13 21:50 ` Ian Lance Taylor
  0 siblings, 0 replies; 2+ messages in thread
From: Ian Lance Taylor @ 2007-08-13 21:50 UTC (permalink / raw)
  To: Rask Ingemann Lambertsen; +Cc: gcc

Rask Ingemann Lambertsen <rask@sygehus.dk> writes:

>    In expr.c, convert_move() tries to synthesize sign extension in modes
> larger than those directly supported by the target. There are two strategies
> for generating the sign bit copies:
> 
> 1) Compare with 0 and use "slt" if STORE_FLAG_VALUE == -1.
> 2) Use a signed right shift of one bit less than the operand width.
> 
>       /* Compute the value to put in each remaining word.  */
>       if (unsignedp)
> 	fill_value = const0_rtx;
>       else
> 	{
> #ifdef HAVE_slt
> 	  if (HAVE_slt
> 	      && insn_data[(int) CODE_FOR_slt].operand[0].mode == word_mode
> 	      && STORE_FLAG_VALUE == -1)
> 	    {
> 	      emit_cmp_insn (lowfrom, const0_rtx, NE, NULL_RTX,
> 			     lowpart_mode, 0);
> 	      fill_value = gen_reg_rtx (word_mode);
> 	      emit_insn (gen_slt (fill_value));
> 	    }
> 	  else
> #endif
> 	    {
> 	      fill_value
> 		= expand_shift (RSHIFT_EXPR, lowpart_mode, lowfrom,
> 				size_int (GET_MODE_BITSIZE (lowpart_mode) - 1),
> 				NULL_RTX, 0);
> 	      fill_value = convert_to_mode (word_mode, fill_value, 1);
> 	    }
> 	}
> 
>    My questions center around the first aproach:
> 
> 1) Shouldn't it check that the comparison is directly supported by the
> target rather than implemented by a library call?

The condition code handling in gcc is more complex than it needs to
be.  The way to generate an slt instruction is what you see above:
emit_cmp_insn followed by gen_slt.  The gen_slt needs to figure out
which operands to compare.  If you have a gen_slt which works in
word_mode, then the comparison instruction is presumed to exist.

There is probably a bug here when lowpart_mode != word_mode.  For most
targets that case can never arise, because there are not two different
sizes of signed integers both of which are larger than word_mode.

> 2) How does it handle failure of gen_slt?

It clearly doesn't.  That is a different bug.

Ian

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2007-08-13 19:11 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2007-08-12 15:13 Sign extension by expr.c convert_move() Rask Ingemann Lambertsen
2007-08-13 21:50 ` Ian Lance Taylor

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).