diff --git a/libstdc++-v3/include/experimental/bits/simd_detail.h b/libstdc++-v3/include/experimental/bits/simd_detail.h
index 30cc1ef0eefd41537ab855ae55f993f2a4801a02..49b94decf0aa9c41b745bb553d9a26c70709a003 100644
--- a/libstdc++-v3/include/experimental/bits/simd_detail.h
+++ b/libstdc++-v3/include/experimental/bits/simd_detail.h
@@ -267,7 +267,7 @@
 #define _GLIBCXX_SIMD_IS_UNLIKELY(__x) __builtin_expect(__x, 0)
 #define _GLIBCXX_SIMD_IS_LIKELY(__x) __builtin_expect(__x, 1)
 
-#if defined __STRICT_ANSI__ && __STRICT_ANSI__
+#if __STRICT_ANSI__ || defined __clang__
 #define _GLIBCXX_SIMD_CONSTEXPR
 #define _GLIBCXX_SIMD_USE_CONSTEXPR_API const
 #else
diff --git a/libstdc++-v3/include/experimental/bits/simd_x86.h b/libstdc++-v3/include/experimental/bits/simd_x86.h
index 608918542c6326d200941362a5ce96d31f41f8b9..7b8f1c664b3e78885e0d67a64083bdf9d15d9eef 100644
--- a/libstdc++-v3/include/experimental/bits/simd_x86.h
+++ b/libstdc++-v3/include/experimental/bits/simd_x86.h
@@ -363,6 +363,53 @@ template <typename _Tp>
 
 // }}}
 
+#ifdef __clang__
+template <size_t _Np, typename _Tp, typename _Kp>
+  _GLIBCXX_SIMD_INTRINSIC constexpr auto
+  __movm(_Kp __k) noexcept
+  {
+    static_assert(is_unsigned_v<_Kp>);
+    if constexpr (sizeof(_Tp) == 1 && __have_avx512bw)
+      {
+	if constexpr (_Np <= 16 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2b128(__k);
+	else if constexpr (_Np <= 32 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2b256(__k);
+	else
+	  return __builtin_ia32_cvtmask2b512(__k);
+      }
+    else if constexpr (sizeof(_Tp) == 2 && __have_avx512bw)
+      {
+	if constexpr (_Np <= 8 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2w128(__k);
+	else if constexpr (_Np <= 16 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2w256(__k);
+	else
+	  return __builtin_ia32_cvtmask2w512(__k);
+      }
+    else if constexpr (sizeof(_Tp) == 4 && __have_avx512dq)
+      {
+	if constexpr (_Np <= 4 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2d128(__k);
+	else if constexpr (_Np <= 8 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2d256(__k);
+	else
+	  return __builtin_ia32_cvtmask2d512(__k);
+      }
+    else if constexpr (sizeof(_Tp) == 8 && __have_avx512dq)
+      {
+	if constexpr (_Np <= 2 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2q128(__k);
+	else if constexpr (_Np <= 4 && __have_avx512vl)
+	  return __builtin_ia32_cvtmask2q256(__k);
+	else
+	  return __builtin_ia32_cvtmask2q512(__k);
+      }
+    else
+      __assert_unreachable<_Tp>();
+  }
+#endif // __clang__
+
 #ifdef _GLIBCXX_SIMD_WORKAROUND_PR85048
 #include "simd_x86_conversions.h"
 #endif
@@ -619,14 +666,13 @@ struct _CommonImplX86 : _CommonImplBuiltin
     _GLIBCXX_SIMD_INTRINSIC static _TV
     _S_blend_avx512(const _Kp __k, const _TV __a, const _TV __b) noexcept
     {
-#ifdef __clang__
-      // FIXME: this does a boolean choice, not a blend
-      return __k ? __a : __b;
-#else
       static_assert(__is_vector_type_v<_TV>);
       using _Tp = typename _VectorTraits<_TV>::value_type;
       static_assert(sizeof(_TV) >= 16);
       static_assert(sizeof(_Tp) <= 8);
+#ifdef __clang__
+      return __movm<_VectorTraits<_TV>::_S_full_size, _Tp>(__k) ? __b : __a;
+#else
       using _IntT
 	= conditional_t<(sizeof(_Tp) > 2),
 			conditional_t<sizeof(_Tp) == 4, int, long long>,
@@ -3483,6 +3529,9 @@ template <typename _Abi, typename>
 	    // optimize masked unary increment and decrement as masked sub +/-1
 	    constexpr int __pm_one
 	      = is_same_v<_Op<void>, __increment<void>> ? -1 : 1;
+#ifdef __clang__
+	    return __movm<_Np, _Tp>(__k._M_data) ? __v._M_data - __pm_one : __v._M_data;
+#else // __clang__
 	    if constexpr (is_integral_v<_Tp>)
 	      {
 		constexpr bool __lp64 = sizeof(long) == sizeof(long long);
@@ -3526,6 +3575,7 @@ template <typename _Abi, typename>
 		_GLIBCXX_SIMD_MASK_SUB(8, 16, subpd128);
 #undef _GLIBCXX_SIMD_MASK_SUB
 	      }
+#endif // __clang__
 	  }
 	else
 	  return _Base::template _S_masked_unary<_Op>(__k, __v);