Patchwork [doc,testsuite,libgfortran] Avoid use of SSE/SSE2/SSE3 on Solaris 8/9 x86

login
register
mail settings
Submitter Rainer Orth
Date July 15, 2010, 10:43 a.m.
Message ID <yddlj9dc9f7.fsf@manam.CeBiTec.Uni-Bielefeld.DE>
Download mbox | patch
Permalink /patch/58970/
State New
Headers show

Comments

Rainer Orth - July 15, 2010, 10:43 a.m.
Uros Bizjak <ubizjak@gmail.com> writes:

> This patch is OK, but please commit it without sse{,2}_runtime changes.

Done after testing on the branches completed.

> Please prepare another incremental patch that includes sse{,2}_runtime
> stuff, we will discuss your approach separatelly.

Right now, this is just the sse{, 2}_runtime part of the original patch
as is.  It seems possible to convert most of the tests to use sse{, 2,
3}-check.h instead, with the exception of the users of isa-check.h.
Beyond, I think we still need the check_effective_target_sse{,
2}_runtime procs for use in lib/fortran-torture.exp and and
gfortran.dg/vect/vect.exp.

Comments?

	Rainer


2010-06-14  Rainer Orth  <ro@CeBiTec.Uni-Bielefeld.DE>

	gcc:
	* doc/sourcebuild.texi (Effective-Target Keywords): Document
	sse_runtime, sse2_runtime.

	gcc/testsuite:
	* lib/target-supports.exp (check_effective_target_sse_runtime):
	New proc.
	(check_effective_target_sse2_runtime): New proc.
	* lib/fortran-torture.exp (get-fortran-torture-options): Only add
	-msse2 if check_effective_target_sse2_runtime.
	* gfortran.dg/vect/vect.exp: Likewise.
	* g++.dg/other/i386-1.C: Use dg-require-effective-target sse2_runtime.
	* g++.dg/other/pr40446.C: Likewise.
	* gcc.dg/compat/union-m128-1_main.c: Likewise.
	* gcc.dg/compat/vector-1a_main.c: Likewise.
	* gcc.dg/compat/vector-2a_main.c: Likewise.
	* gcc.dg/pr36584.c: Likewise.
	* gcc.dg/pr37544.c: Likewise.
	* gcc.dg/torture/pr16104-1.c: Likewise.
	* gcc.dg/torture/pr35771-1.c: Likewise.
	* gcc.dg/torture/pr35771-2.c: Likewise.
	* gcc.dg/torture/pr35771-3.c: Likewise.
	* gcc.dg/torture/stackalign/alloca-2.c: Likewise.
	* gcc.dg/torture/stackalign/alloca-3.c: Likewise.
	* gcc.dg/torture/stackalign/push-1.c: Likewise.
	* gcc.dg/torture/stackalign/vararg-3.c: Likewise.
	* gcc.target/i386/pr39315-2.c: Likewise.
	* gcc.target/i386/pr39315-4.c: Likewise.
	* gcc.target/i386/vperm-v2df.c: Likewise.
	* gcc.target/i386/vperm-v2di.c: Likewise.
	* gcc.target/i386/vperm-v4sf-1.c: Use dg-require-effective-target
	sse_runtime.
	* gcc.target/i386/vperm-v4si-1.c: Use dg-require-effective-target
	sse2_runtime.
Uros Bizjak - July 15, 2010, 12:20 p.m.
On Thu, Jul 15, 2010 at 12:43 PM, Rainer Orth
<ro@cebitec.uni-bielefeld.de> wrote:
> Uros Bizjak <ubizjak@gmail.com> writes:
>
>> This patch is OK, but please commit it without sse{,2}_runtime changes.
>
> Done after testing on the branches completed.
>
>> Please prepare another incremental patch that includes sse{,2}_runtime
>> stuff, we will discuss your approach separatelly.
>
> Right now, this is just the sse{, 2}_runtime part of the original patch
> as is.  It seems possible to convert most of the tests to use sse{, 2,
> 3}-check.h instead, with the exception of the users of isa-check.h.
> Beyond, I think we still need the check_effective_target_sse{,
> 2}_runtime procs for use in lib/fortran-torture.exp and and
> gfortran.dg/vect/vect.exp.
>
> Comments?

I don't think we need separate check_sse_runtime and
check_sse2_runtime. There are no separate sse and sse2 registers (they
are called xmm registers). FYI, mmx regs are aliased to x87 register
stack and are not affected by this problem.

So, I propose to

a) Add only check_sse_os_support_available check
b) Search for all vect.exp files and add this check together with
check_sse2_hw_available to fix vect testsuites
c) Introduce new check_effective_target_sse2_runtime. Put
check_sse2_hw_available and check_sse_os_support_available into this
function (in a similar way as vect.exp does).
c1) Eventually, introduce check_effective_target_sse_runtime and
corresponding sse_hw_available.
d) You can then remove all homegrown runtime checks for SSE from the testcases.

I would also prefer to unify solaris check in i386.md IMO, it is
enough to check "movss %xmm2, %xmm1" for all SSE levels. This would
remove complications with ILL_INSN, since it will always be the same
and thus part of sol2-check.

BTW: I think you will need to change all *-check.h checks (minus
MMX/3dNOW! ones) to prevent tests from touching xmm regs.

Uros.
Rainer Orth - July 15, 2010, 2:42 p.m.
Uros Bizjak <ubizjak@gmail.com> writes:

> I don't think we need separate check_sse_runtime and
> check_sse2_runtime. There are no separate sse and sse2 registers (they
> are called xmm registers). FYI, mmx regs are aliased to x87 register
> stack and are not affected by this problem.

Ok, fine.

> So, I propose to
>
> a) Add only check_sse_os_support_available check
> b) Search for all vect.exp files and add this check together with
> check_sse2_hw_available to fix vect testsuites
> c) Introduce new check_effective_target_sse2_runtime. Put
> check_sse2_hw_available and check_sse_os_support_available into this
> function (in a similar way as vect.exp does).
> c1) Eventually, introduce check_effective_target_sse_runtime and
> corresponding sse_hw_available.

Sounds reasonable so far.

> d) You can then remove all homegrown runtime checks for SSE from the testcases.

What do you mean with `homegrown runtime checks' here?  I suppose all
the `manual' invocations of __get_cpuid() outside of gcc.target/i386?
That would work nicely: the existing dg-require-effective-target
sse*_runtime tests could be left in place and the tests would magically
work without the testcase having to do the check itself.  That's even
better than converting them to use sse*-check.h, which would have to be
located from outside of gcc.target/i386.

> I would also prefer to unify solaris check in i386.md IMO, it is

I suppose you mean sol2-check.h (ILL_INSN and ILL_INSN_LEN) here?

> enough to check "movss %xmm2, %xmm1" for all SSE levels. This would
> remove complications with ILL_INSN, since it will always be the same
> and thus part of sol2-check.

Right.  Perhaps we should rename sol2-check.h to sse-os-support.h and
sol2_check() to sse_os_support() at this point to match the dg procs?
There's nothing Solaris-specific left in the interface, and if ever
another OS comes along with a similar problem, only the header needs to
be augmented.

> BTW: I think you will need to change all *-check.h checks (minus
> MMX/3dNOW! ones) to prevent tests from touching xmm regs.

For complete correctness, you're certainly right.  On the other hand,
Solaris 8 and 9 won't run on very recent processors, so I've only
changed those *-check.h tests that exhibited execution failures.  I can
of course change all the *-check.h checks for generality if you prefer.

Thanks.
	Rainer
Uros Bizjak - July 15, 2010, 3:27 p.m.
On Thu, Jul 15, 2010 at 4:42 PM, Rainer Orth
<ro@cebitec.uni-bielefeld.de> wrote:

>> d) You can then remove all homegrown runtime checks for SSE from the testcases.
>
> What do you mean with `homegrown runtime checks' here?  I suppose all
> the `manual' invocations of __get_cpuid() outside of gcc.target/i386?
> That would work nicely: the existing dg-require-effective-target
> sse*_runtime tests could be left in place and the tests would magically
> work without the testcase having to do the check itself.  That's even
> better than converting them to use sse*-check.h, which would have to be
> located from outside of gcc.target/i386.

Yes, I was looking on __get_cpuid() handling in various testcases.

>> I would also prefer to unify solaris check in i386.md IMO, it is
>
> I suppose you mean sol2-check.h (ILL_INSN and ILL_INSN_LEN) here?

Uhm, yes. I have mixed a bit between many projects, I was thinking on
gcc.target/i386 test directory.

>> enough to check "movss %xmm2, %xmm1" for all SSE levels. This would
>> remove complications with ILL_INSN, since it will always be the same
>> and thus part of sol2-check.
>
> Right.  Perhaps we should rename sol2-check.h to sse-os-support.h and
> sol2_check() to sse_os_support() at this point to match the dg procs?
> There's nothing Solaris-specific left in the interface, and if ever
> another OS comes along with a similar problem, only the header needs to
> be augmented.

I think your proposal is very good.

>> BTW: I think you will need to change all *-check.h checks (minus
>> MMX/3dNOW! ones) to prevent tests from touching xmm regs.
>
> For complete correctness, you're certainly right.  On the other hand,
> Solaris 8 and 9 won't run on very recent processors, so I've only
> changed those *-check.h tests that exhibited execution failures.  I can
> of course change all the *-check.h checks for generality if you prefer.

Ah, I see. I'll leave this to you. Perhaps you could put a comment in
net sse-os-support.h, why partial check is OK.

Thanks.
Uros.

Patch

diff -r 8e384a980ea3 gcc/doc/sourcebuild.texi
--- a/gcc/doc/sourcebuild.texi	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/doc/sourcebuild.texi	Fri Jul 09 23:02:22 2010 +0200
@@ -1607,9 +1607,15 @@ 
 @item sse
 Target supports compiling @code{sse} instructions.
 
+@item sse_runtime
+Target supports the execution of @code{sse} instructions.
+
 @item sse2
 Target supports compiling @code{sse2} instructions.
 
+@item sse2_runtime
+Target supports the execution of @code{sse2} instructions.
+
 @item sync_char_short
 Target supports atomic operations on @code{char} and @code{short}.
 
diff -r 8e384a980ea3 gcc/testsuite/g++.dg/other/i386-1.C
--- a/gcc/testsuite/g++.dg/other/i386-1.C	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/g++.dg/other/i386-1.C	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run { target i?86-*-* x86_64-*-* } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include <xmmintrin.h>
 
diff -r 8e384a980ea3 gcc/testsuite/g++.dg/other/pr40446.C
--- a/gcc/testsuite/g++.dg/other/pr40446.C	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/g++.dg/other/pr40446.C	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 // { dg-do run { target i?86-*-* x86_64-*-* } }
 // { dg-options "-O1 -msse2" }
 // { dg-require-effective-target sse2 }
+// { dg-require-effective-target sse2_runtime }
 
 #include <emmintrin.h>
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/compat/union-m128-1_main.c
--- a/gcc/testsuite/gcc.dg/compat/union-m128-1_main.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/compat/union-m128-1_main.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-skip-if "test SSE2 support" { ! { i?86-*-* x86_64-*-* } } } */
 /* { dg-options "-O" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include "cpuid.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/compat/vector-1a_main.c
--- a/gcc/testsuite/gcc.dg/compat/vector-1a_main.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/compat/vector-1a_main.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,5 +1,6 @@ 
 /* { dg-skip-if "test SSE2 vector" { ! { i?86-*-* x86_64-*-* } } } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 /* Test compatibility of vector types: layout between separately-compiled
    modules, parameter passing, and function return.  This test uses
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/compat/vector-2a_main.c
--- a/gcc/testsuite/gcc.dg/compat/vector-2a_main.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/compat/vector-2a_main.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,5 +1,6 @@ 
 /* { dg-skip-if "test SSE2 support" { ! { i?86-*-* x86_64-*-* } } } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 /* Test compatibility of vector types: layout between separately-compiled
    modules, parameter passing, and function return.  This test uses
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/pr36584.c
--- a/gcc/testsuite/gcc.dg/pr36584.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/pr36584.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-options "-O2 -lm" } */
 /* { dg-options "-O2 -msse2 -mfpmath=sse" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-require-effective-target sse2 { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
+/* { dg-require-effective-target sse2_runtime { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 
 #ifdef __i386__
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/pr37544.c
--- a/gcc/testsuite/gcc.dg/pr37544.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/pr37544.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-options "-O2" } */
 /* { dg-options "-O2 -msse2 -mtune=core2 -mfpmath=387" { target { i?86-*-* x86_64-*-* } } } */
 /* { dg-require-effective-target sse2 { target { i?86-*-* x86_64-*-* } } } */
+/* { dg-require-effective-target sse2_runtime { target { i?86-*-* x86_64-*-* } } } */
 
 #ifdef __i386__
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/pr16104-1.c
--- a/gcc/testsuite/gcc.dg/torture/pr16104-1.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/pr16104-1.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run { target i?86-*-* x86_64-*-* } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include "cpuid.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/pr35771-1.c
--- a/gcc/testsuite/gcc.dg/torture/pr35771-1.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/pr35771-1.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run { target i?86-*-* x86_64-*-* } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 typedef float __m128 __attribute__ ((__vector_size__ (16), __may_alias__));
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/pr35771-2.c
--- a/gcc/testsuite/gcc.dg/torture/pr35771-2.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/pr35771-2.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run { target i?86-*-* x86_64-*-* } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 typedef double __m128d __attribute__ ((__vector_size__ (16), __may_alias__));
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/pr35771-3.c
--- a/gcc/testsuite/gcc.dg/torture/pr35771-3.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/pr35771-3.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run { target i?86-*-* x86_64-*-* } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 typedef long long __m128i __attribute__ ((__vector_size__ (16), __may_alias__));
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/stackalign/alloca-2.c
--- a/gcc/testsuite/gcc.dg/torture/stackalign/alloca-2.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/stackalign/alloca-2.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include <emmintrin.h>
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/stackalign/alloca-3.c
--- a/gcc/testsuite/gcc.dg/torture/stackalign/alloca-3.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/stackalign/alloca-3.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include <emmintrin.h>
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/stackalign/push-1.c
--- a/gcc/testsuite/gcc.dg/torture/stackalign/push-1.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/stackalign/push-1.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-msse2 -mpreferred-stack-boundary=2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include <emmintrin.h>
 #include "cpuid.h"
diff -r 8e384a980ea3 gcc/testsuite/gcc.dg/torture/stackalign/vararg-3.c
--- a/gcc/testsuite/gcc.dg/torture/stackalign/vararg-3.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.dg/torture/stackalign/vararg-3.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include <stdarg.h>
 #include <emmintrin.h>
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/pr39315-2.c
--- a/gcc/testsuite/gcc.target/i386/pr39315-2.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/pr39315-2.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse2 -mtune=generic" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 /* { dg-additional-sources pr39315-check.c } */
 
 typedef float __m128 __attribute__ ((__vector_size__ (16)));
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/pr39315-4.c
--- a/gcc/testsuite/gcc.target/i386/pr39315-4.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/pr39315-4.c	Fri Jul 09 23:02:22 2010 +0200
@@ -2,6 +2,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse2 -mtune=generic" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 /* { dg-additional-sources pr39315-check.c } */
 
 typedef float __m128 __attribute__ ((__vector_size__ (16)));
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/vperm-v2df.c
--- a/gcc/testsuite/gcc.target/i386/vperm-v2df.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/vperm-v2df.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include "isa-check.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/vperm-v2di.c
--- a/gcc/testsuite/gcc.target/i386/vperm-v2di.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/vperm-v2di.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include "isa-check.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/vperm-v4sf-1.c
--- a/gcc/testsuite/gcc.target/i386/vperm-v4sf-1.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/vperm-v4sf-1.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,5 +1,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse" } */
+/* { dg-require-effective-target sse } */
+/* { dg-require-effective-target sse_runtime } */
 
 #include "isa-check.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gcc.target/i386/vperm-v4si-1.c
--- a/gcc/testsuite/gcc.target/i386/vperm-v4si-1.c	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gcc.target/i386/vperm-v4si-1.c	Fri Jul 09 23:02:22 2010 +0200
@@ -1,6 +1,7 @@ 
 /* { dg-do run } */
 /* { dg-options "-O -msse2" } */
 /* { dg-require-effective-target sse2 } */
+/* { dg-require-effective-target sse2_runtime } */
 
 #include "isa-check.h"
 
diff -r 8e384a980ea3 gcc/testsuite/gfortran.dg/vect/vect.exp
--- a/gcc/testsuite/gfortran.dg/vect/vect.exp	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/gfortran.dg/vect/vect.exp	Fri Jul 09 23:02:22 2010 +0200
@@ -68,7 +68,8 @@ 
 } elseif { [istarget  "spu-*-*"] } {
    set dg-do-what-default run
 } elseif { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"] } {
-    if { ![check_effective_target_sse2] } then {
+    if { ![check_effective_target_sse2]
+	 || ![check_effective_target_sse2_runtime]} then {
 	return
     }
     lappend DEFAULT_VECTCFLAGS "-msse2"
diff -r 8e384a980ea3 gcc/testsuite/lib/fortran-torture.exp
--- a/gcc/testsuite/lib/fortran-torture.exp	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/lib/fortran-torture.exp	Fri Jul 09 23:02:22 2010 +0200
@@ -46,7 +46,8 @@ 
 	set test_tree_vectorize 1
     } elseif { ( [istarget "i?86-*-*"] || [istarget "x86_64-*-*"] )
 	       && [check_effective_target_sse2]
-	       && [check_sse2_hw_available] } {
+	       && [check_sse2_hw_available]
+	       && [check_effective_target_sse2_runtime] } {
 	lappend vectorizer_options "-msse2"
 	set test_tree_vectorize 1
     } elseif { [istarget "mips*-*-*"]
diff -r 8e384a980ea3 gcc/testsuite/lib/target-supports.exp
--- a/gcc/testsuite/lib/target-supports.exp	Fri Jul 09 22:58:08 2010 +0200
+++ b/gcc/testsuite/lib/target-supports.exp	Fri Jul 09 23:02:22 2010 +0200
@@ -910,6 +910,42 @@ 
     }]
 }
 
+# Return 1 if the target supports running SSE executables, 0 otherwise.
+
+proc check_effective_target_sse_runtime { } {
+    # The Solaris 2 kernel doesn't save and restore SSE registers before
+    # Solaris 9 4/04.  Before that, executables die with SIGILL.
+    if { [istarget i?86-*-solaris2*] } {
+	check_runtime sse_execute {
+	    int main ()
+	    {
+		__asm__ volatile ("movss %xmm2,%xmm1");
+		return 0;
+	    }
+	} "-msse"
+    } else {
+	return 1
+    }
+}
+
+# Return 1 if the target supports running SSE2 executables, 0 otherwise.
+
+proc check_effective_target_sse2_runtime { } {
+    # The Solaris 2 kernel doesn't save and restore SSE2 registers before
+    # Solaris 9 4/04.  Before that, executables die with SIGILL.
+    if { [istarget i?86-*-solaris2*] } {
+	check_runtime sse2_execute {
+	    int main ()
+	    {
+		__asm__ volatile ("unpcklpd %xmm0,%xmm2");
+		return 0;
+	    }
+	} "-msse2"
+    } else {
+	return 1
+    }
+}
+
 # Return 1 if the target supports executing SSE2 instructions, 0
 # otherwise.  Cache the result.