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.
 
