re PR target/6753 (gcc 3.1 produces wrong code when optimizing for pentium4)

PR target/6753
	* config/i386/i386.md (sse_movdfcc, sse_movdfcc_eq): Use Y instead
	of x in constraints for clarity.
	(sse_mov?fcc split): abort if op2 == op3.
	(sse_movsfcc_const0_1, sse_movsfcc_const0_2, sse_movsfcc_const0_3,
	sse_movsfcc_const0_4): Add earlyclobber.
	(sse_movdfcc_const0_1, sse_movdfcc_const0_2, sse_movdfcc_const0_3,
	sse_movdfcc_const0_4): Likewise.  Use DFmode, not SFmode.
	Use Y instead of x in constraints.

	* gcc.dg/20020523-1.c: New test.

From-SVN: r53784
This commit is contained in:
Jakub Jelinek 2002-05-23 11:29:29 +02:00 committed by Jakub Jelinek
parent 9217ef40d1
commit 66b408f2b0
4 changed files with 123 additions and 38 deletions

View File

@ -1,3 +1,15 @@
2002-05-23 Jakub Jelinek <jakub@redhat.com>
PR target/6753
* config/i386/i386.md (sse_movdfcc, sse_movdfcc_eq): Use Y instead
of x in constraints for clarity.
(sse_mov?fcc split): abort if op2 == op3.
(sse_movsfcc_const0_1, sse_movsfcc_const0_2, sse_movsfcc_const0_3,
sse_movsfcc_const0_4): Add earlyclobber.
(sse_movdfcc_const0_1, sse_movdfcc_const0_2, sse_movdfcc_const0_3,
sse_movdfcc_const0_4): Likewise. Use DFmode, not SFmode.
Use Y instead of x in constraints.
2002-05-23 Richard Henderson <rth@redhat.com>
* doc/extend.texi (C99 Thread-Local Edits): New subsection.

View File

@ -15949,12 +15949,12 @@
"#")
(define_insn "sse_movdfcc"
[(set (match_operand:DF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?f#xr,?f#xr,?r#xf,?r#xf,?r#xf,?r#xf")
[(set (match_operand:DF 0 "register_operand" "=&Y#rf,Y#rf,?f#Yr,?f#Yr,?f#Yr,?f#Yr,?r#Yf,?r#Yf,?r#Yf,?r#Yf")
(if_then_else:DF (match_operator 1 "sse_comparison_operator"
[(match_operand:DF 4 "nonimmediate_operand" "0#fx,x#fx,f#x,f#x,xm#f,xm#f,f#x,f#x,xm#f,xm#f")
(match_operand:DF 5 "nonimmediate_operand" "xm#f,xm#f,f#x,f#x,x#f,x#f,f#x,f#x,x#f,x#f")])
(match_operand:DF 2 "nonimmediate_operand" "x#fr,0#fr,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx,0#rx")
(match_operand:DF 3 "nonimmediate_operand" "x#fr,x#fr,0#fx,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx")))
[(match_operand:DF 4 "nonimmediate_operand" "0#fY,Y#fY,f#Y,f#Y,Ym#f,Ym#f,f#Y,f#Y,Ym#f,Ym#f")
(match_operand:DF 5 "nonimmediate_operand" "Ym#f,Ym#f,f#Y,f#Y,Y#f,Y#f,f#Y,f#Y,Y#f,Y#f")])
(match_operand:DF 2 "nonimmediate_operand" "Y#fr,0#fr,f#fY,0#fY,f#fY,0#fY,rm#rY,0#rY,rm#rY,0#rY")
(match_operand:DF 3 "nonimmediate_operand" "Y#fr,Y#fr,0#fY,f#fY,0#fY,f#fY,0#fY,rm#rY,0#rY,rm#rY")))
(clobber (match_scratch:DF 6 "=2,&4,X,X,X,X,X,X,X,X"))
(clobber (reg:CC 17))]
"TARGET_SSE2
@ -15964,11 +15964,11 @@
"#")
(define_insn "sse_movdfcc_eq"
[(set (match_operand:DF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?r#xf,?r#xf")
(if_then_else:DF (eq (match_operand:DF 3 "nonimmediate_operand" "%0#fx,x#fx,f#x,xm#f,f#x,xm#f")
(match_operand:DF 4 "nonimmediate_operand" "xm#f,xm#f,f#x,x#f,f#x,x#f"))
(match_operand:DF 1 "nonimmediate_operand" "x#fr,0#fr,0#fx,0#fx,0#rx,0#rx")
(match_operand:DF 2 "nonimmediate_operand" "x#fr,x#fr,f#fx,f#fx,rm#rx,rm#rx")))
[(set (match_operand:DF 0 "register_operand" "=&Y#rf,Y#rf,?f#Yr,?f#Yr,?r#Yf,?r#Yf")
(if_then_else:DF (eq (match_operand:DF 3 "nonimmediate_operand" "%0#fY,Y#fY,f#Y,Ym#f,f#Y,Ym#f")
(match_operand:DF 4 "nonimmediate_operand" "Ym#f,Ym#f,f#Y,Y#f,f#Y,Y#f"))
(match_operand:DF 1 "nonimmediate_operand" "Y#fr,0#fr,0#fY,0#fY,0#rY,0#rY")
(match_operand:DF 2 "nonimmediate_operand" "Y#fr,Y#fr,f#fY,f#fY,rm#rY,rm#rY")))
(clobber (match_scratch:DF 5 "=1,&3,X,X,X,X"))
(clobber (reg:CC 17))]
"TARGET_SSE
@ -16020,6 +16020,10 @@
(set (subreg:TI (match_dup 0) 0) (ior:TI (subreg:TI (match_dup 6) 0)
(subreg:TI (match_dup 7) 0)))]
{
/* If op2 == op3, op3 will be clobbered before it is used.
This should be optimized out though. */
if (operands_match_p (operands[2], operands[3]))
abort ();
PUT_MODE (operands[1], GET_MODE (operands[0]));
if (operands_match_p (operands[0], operands[4]))
operands[6] = operands[4], operands[7] = operands[2];
@ -16031,7 +16035,7 @@
;; Do not brother with the integer/floating point case, since these are
;; bot considerably slower, unlike in the generic case.
(define_insn "*sse_movsfcc_const0_1"
[(set (match_operand:SF 0 "register_operand" "=x")
[(set (match_operand:SF 0 "register_operand" "=&x")
(if_then_else:SF (match_operator 1 "sse_comparison_operator"
[(match_operand:SF 4 "register_operand" "0")
(match_operand:SF 5 "nonimmediate_operand" "xm")])
@ -16041,7 +16045,7 @@
"#")
(define_insn "*sse_movsfcc_const0_2"
[(set (match_operand:SF 0 "register_operand" "=x")
[(set (match_operand:SF 0 "register_operand" "=&x")
(if_then_else:SF (match_operator 1 "sse_comparison_operator"
[(match_operand:SF 4 "register_operand" "0")
(match_operand:SF 5 "nonimmediate_operand" "xm")])
@ -16051,7 +16055,7 @@
"#")
(define_insn "*sse_movsfcc_const0_3"
[(set (match_operand:SF 0 "register_operand" "=x")
[(set (match_operand:SF 0 "register_operand" "=&x")
(if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:SF 4 "nonimmediate_operand" "xm")
(match_operand:SF 5 "register_operand" "0")])
@ -16061,7 +16065,7 @@
"#")
(define_insn "*sse_movsfcc_const0_4"
[(set (match_operand:SF 0 "register_operand" "=x")
[(set (match_operand:SF 0 "register_operand" "=&x")
(if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:SF 4 "nonimmediate_operand" "xm")
(match_operand:SF 5 "register_operand" "0")])
@ -16071,42 +16075,42 @@
"#")
(define_insn "*sse_movdfcc_const0_1"
[(set (match_operand:SF 0 "register_operand" "=x")
(if_then_else:SF (match_operator 1 "sse_comparison_operator"
[(match_operand:SF 4 "register_operand" "0")
(match_operand:SF 5 "nonimmediate_operand" "xm")])
(match_operand:SF 2 "register_operand" "x")
(match_operand:SF 3 "const0_operand" "X")))]
[(set (match_operand:DF 0 "register_operand" "=&Y")
(if_then_else:DF (match_operator 1 "sse_comparison_operator"
[(match_operand:DF 4 "register_operand" "0")
(match_operand:DF 5 "nonimmediate_operand" "Ym")])
(match_operand:DF 2 "register_operand" "Y")
(match_operand:DF 3 "const0_operand" "X")))]
"TARGET_SSE2"
"#")
(define_insn "*sse_movdfcc_const0_2"
[(set (match_operand:SF 0 "register_operand" "=x")
(if_then_else:SF (match_operator 1 "sse_comparison_operator"
[(match_operand:SF 4 "register_operand" "0")
(match_operand:SF 5 "nonimmediate_operand" "xm")])
(match_operand:SF 2 "const0_operand" "X")
(match_operand:SF 3 "register_operand" "x")))]
[(set (match_operand:DF 0 "register_operand" "=&Y")
(if_then_else:DF (match_operator 1 "sse_comparison_operator"
[(match_operand:DF 4 "register_operand" "0")
(match_operand:DF 5 "nonimmediate_operand" "Ym")])
(match_operand:DF 2 "const0_operand" "X")
(match_operand:DF 3 "register_operand" "Y")))]
"TARGET_SSE2"
"#")
(define_insn "*sse_movdfcc_const0_3"
[(set (match_operand:SF 0 "register_operand" "=x")
(if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:SF 4 "nonimmediate_operand" "xm")
(match_operand:SF 5 "register_operand" "0")])
(match_operand:SF 2 "register_operand" "x")
(match_operand:SF 3 "const0_operand" "X")))]
[(set (match_operand:DF 0 "register_operand" "=&Y")
(if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:DF 4 "nonimmediate_operand" "Ym")
(match_operand:DF 5 "register_operand" "0")])
(match_operand:DF 2 "register_operand" "Y")
(match_operand:DF 3 "const0_operand" "X")))]
"TARGET_SSE2"
"#")
(define_insn "*sse_movdfcc_const0_4"
[(set (match_operand:SF 0 "register_operand" "=x")
(if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:SF 4 "nonimmediate_operand" "xm")
(match_operand:SF 5 "register_operand" "0")])
(match_operand:SF 2 "const0_operand" "X")
(match_operand:SF 3 "register_operand" "x")))]
[(set (match_operand:DF 0 "register_operand" "=&Y")
(if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
[(match_operand:DF 4 "nonimmediate_operand" "Ym")
(match_operand:DF 5 "register_operand" "0")])
(match_operand:DF 2 "const0_operand" "X")
(match_operand:DF 3 "register_operand" "Y")))]
"TARGET_SSE2"
"#")

View File

@ -1,3 +1,7 @@
2002-05-23 Jakub Jelinek <jakub@redhat.com>
* gcc.dg/20020523-1.c: New test.
2002-05-23 Neil Booth <neil@daikokuya.demon.co.uk>
* objc.dg/const-str-2.m: Update now that we stop after

View File

@ -0,0 +1,65 @@
/* PR target/6753
This testcase was miscompiled because sse_mov?fcc_const0*
patterns were missing earlyclobber. */
/* { dg-do run { target i386-*-* } } */
/* { dg-options "-march=pentium3 -msse -ffast-math -O2" } */
extern void abort (void);
extern void exit (int);
float one = 1.f;
void bar (float f)
{
if (__builtin_memcmp (&one, &f, sizeof (float)))
abort ();
}
float foo (void)
{
return 1.f;
}
typedef struct
{
float t;
} T;
void bail_if_no_sse (void)
{
int fl1, fl2;
/* See if we can use cpuid. */
__asm__ ("pushfl; pushfl; popl %0; movl %0,%1; xorl %2,%0;"
"pushl %0; popfl; pushfl; popl %0; popfl"
: "=&r" (fl1), "=&r" (fl2)
: "i" (0x00200000));
if (((fl1 ^ fl2) & 0x00200000) == 0)
exit (0);
/* See if cpuid gives capabilities. */
__asm__ ("cpuid" : "=a" (fl1) : "0" (0) : "ebx", "ecx", "edx", "cc");
if (fl1 == 0)
exit (0);
/* See if capabilities include SSE (25th bit; 26 for SSE2). */
__asm__ ("cpuid" : "=a" (fl1), "=d" (fl2) : "0" (1) : "ebx", "ecx", "cc");
if ((fl2 & (1 << 25)) == 0)
exit (0);
}
int main (void)
{
int i;
T x[1];
bail_if_no_sse ();
for (i = 0; i < 1; i++)
{
x[i].t = foo ();
x[i].t = 0.f > x[i].t ? 0.f : x[i].t;
bar (x[i].t);
}
exit (0);
}