re PR middle-end/37807 (Exponential compile time with MMX builtins.)

PR middle-end/37807
	PR middle-end/37809
	* combine.c (force_to_mode): Do not process vector types.

	* rtlanal.c (nonzero_bits1): Do not process vector types.
	(num_sign_bit_copies1): Likewise.

testsuite/ChangeLog

	PR middle-end/37807
	PR middle-end/37809
	* gcc/testsuite/gcc.target/i386/mmx-8.c: New test.

From-SVN: r141732
This commit is contained in:
Ralph Loader 2008-11-10 10:08:15 +01:00 committed by Uros Bizjak
parent 75223c1753
commit ff596cd202
5 changed files with 164 additions and 7 deletions

View File

@ -1,3 +1,12 @@
2008-11-10 Ralph Loader <suckfish@ihug.co.nz>
PR middle-end/37807
PR middle-end/37809
* combine.c (force_to_mode): Do not process vector types.
* rtlanal.c (nonzero_bits1): Do not process vector types.
(num_sign_bit_copies1): Likewise.
2008-11-09 Thomas Schwinge <tschwinge@gnu.org>
* config/i386/gnu.h: Add copyright and licensing header.

View File

@ -7323,6 +7323,10 @@ force_to_mode (rtx x, enum machine_mode mode, unsigned HOST_WIDE_INT mask,
&& (GET_MODE_MASK (GET_MODE (x)) & ~mask) == 0)
return gen_lowpart (mode, x);
/* The arithmetic simplifications here do the wrong thing on vector modes. */
if (VECTOR_MODE_P (mode) || VECTOR_MODE_P (GET_MODE (x)))
return gen_lowpart (mode, x);
switch (code)
{
case CLOBBER:

View File

@ -3681,8 +3681,9 @@ nonzero_bits1 (const_rtx x, enum machine_mode mode, const_rtx known_x,
enum rtx_code code;
unsigned int mode_width = GET_MODE_BITSIZE (mode);
/* For floating-point values, assume all bits are needed. */
if (FLOAT_MODE_P (GET_MODE (x)) || FLOAT_MODE_P (mode))
/* For floating-point and vector values, assume all bits are needed. */
if (FLOAT_MODE_P (GET_MODE (x)) || FLOAT_MODE_P (mode)
|| VECTOR_MODE_P (GET_MODE (x)) || VECTOR_MODE_P (mode))
return nonzero;
/* If X is wider than MODE, use its mode instead. */
@ -4195,7 +4196,8 @@ num_sign_bit_copies1 (const_rtx x, enum machine_mode mode, const_rtx known_x,
if (mode == VOIDmode)
mode = GET_MODE (x);
if (mode == VOIDmode || FLOAT_MODE_P (mode) || FLOAT_MODE_P (GET_MODE (x)))
if (mode == VOIDmode || FLOAT_MODE_P (mode) || FLOAT_MODE_P (GET_MODE (x))
|| VECTOR_MODE_P (GET_MODE (x)) || VECTOR_MODE_P (mode))
return 1;
/* For a smaller object, just ignore the high bits. */

View File

@ -1,7 +1,13 @@
2008-11-02 Ralph Loader <suckfish@ihug.co.nz>
PR middle-end/37807
PR middle-end/37809
* gcc/testsuite/gcc.target/i386/mmx-8.c: New test.
2008-11-09 Paul Thomas <pault@gcc.gnu.org>
PR fortran/37836
* gfortran.dg/minmaxval_1.f90: New test.
PR fortran/37836
* gfortran.dg/minmaxval_1.f90: New test.
2008-11-09 Eric Botcazou <ebotcazou@adacore.com>
@ -17,8 +23,7 @@
2008-11-07 Kaveh R. Ghazi <ghazi@caip.rutgers.edu>
* g++.dg/ipa/iinline-1.C: Remove -c flag, add -fpie for PIC
targets.
* g++.dg/ipa/iinline-1.C: Remove -c flag, add -fpie for PIC targets.
* gcc.dg/tree-ssa/inline-2.c (foo): Add 'inline' keyword.

View File

@ -0,0 +1,137 @@
/* PR middle-end/37809 */
/* { dg-do run } */
/* { dg-options "-O2 -mmmx" } */
#include <mmintrin.h>
#include "mmx-check.h"
// Various tests of cases where it is incorrect to optimise vectors as if they
// were integers of the same width.
extern void abort (void);
void __attribute__ ((noinline))
Sshift()
{
volatile __m64 y = (__m64) 0xffffffffll;
__m64 x = y & (__m64) 0xffffffffll;
x = _m_psradi (x, 1);
x &= (__m64) 0x80000000ll;
if (0 == (long long) x)
abort();
}
#define SHIFTU(F,B,S,T) \
void F() \
{ \
volatile __m64 y = (__m64) 0ll; \
__m64 x = y | (__m64) (1llu << B); \
if (S > 0) \
x = _m_pslldi (x, S); \
else \
x = _m_psrldi (x, -S); \
if (T > 0) \
x = _m_pslldi (x, T); \
else \
x = _m_psrldi (x, -T); \
x &= (__m64) (1llu << (B + S + T)); \
if ((long long) x) \
abort(); \
}
SHIFTU (shiftU1, 31, 1, -1)
SHIFTU (shiftU2, 32, -1, 1)
SHIFTU (shiftU3, 31, 1, 0)
SHIFTU (shiftU4, 32, -1, 0)
void __attribute__ ((noinline))
add_1()
{
volatile long long ONE = 1;
long long one = ONE;
__m64 a = (__m64) one;
__m64 b = (__m64) -one;
__m64 c = a + b;
if (0 == (long long) c)
abort();
}
void __attribute__ ((noinline))
add_2()
{
volatile long long ONE = 1;
long long one = ONE;
__m64 a = (__m64) one;
__m64 b = (__m64) -one;
__m64 c = _m_paddd (a, b);
if (0 == (long long) c)
abort();
}
void __attribute__ ((noinline))
mult_1()
{
volatile __m64 y = (__m64) 0ll;
__m64 x = y | (__m64) (1ll << 32);
x = x * (__m64) 1ll;
x &= (__m64) (1ll << 32);
if (0 != (long long) x)
abort();
}
void __attribute__ ((noinline))
mult_2()
{
volatile int foo = 1;
unsigned long long one = foo & 1;
__m64 x = (__m64) (one << 16);
x *= x;
x &= (__m64) (1ll << 32);
if (0 != (long long) x)
abort();
}
void __attribute__ ((noinline))
mult_3()
{
volatile __m64 y = (__m64) (1ll << 32);
__m64 a = y;
__m64 b = y * (__m64) 1ll;
if (((long long) a) == (long long) b)
abort();
}
void __attribute__ ((noinline))
div_1()
{
volatile __m64 y = (__m64) 0ll;
__m64 x = y | (__m64) (1ull << 32);
x |= (__m64) 1ull;
x = x / x;
if (1ll == (long long) x)
abort();
}
void mmx_test (void)
{
Sshift();
shiftU1();
shiftU2();
shiftU3();
shiftU4();
add_1();
add_2();
mult_1();
mult_2();
mult_3();
div_1();
}