[libc-commits] [libc] [libc] Add check for support and a test for libc SIMD helpers (PR #157746)

via libc-commits libc-commits at lists.llvm.org
Tue Sep 9 13:47:01 PDT 2025


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-libc

Author: Joseph Huber (jhuber6)

<details>
<summary>Changes</summary>

Summary:
This adds a few basic tests for the SIMD helpers and adds a CMake
variable we can use to detect support.


---
Full diff: https://github.com/llvm/llvm-project/pull/157746.diff


4 Files Affected:

- (modified) libc/cmake/modules/CheckCompilerFeatures.cmake (+3) 
- (added) libc/cmake/modules/compiler_features/check_ext_vector_type.cpp (+7) 
- (modified) libc/test/src/__support/CPP/CMakeLists.txt (+12) 
- (added) libc/test/src/__support/CPP/simd_test.cpp (+70) 


``````````diff
diff --git a/libc/cmake/modules/CheckCompilerFeatures.cmake b/libc/cmake/modules/CheckCompilerFeatures.cmake
index a5ea66a5935b7..4d50d81e0ce45 100644
--- a/libc/cmake/modules/CheckCompilerFeatures.cmake
+++ b/libc/cmake/modules/CheckCompilerFeatures.cmake
@@ -15,6 +15,7 @@ set(
     "fixed_point"
     "cfloat16"
     "cfloat128"
+    "ext_vector_type"
 )
 
 # Making sure ALL_COMPILER_FEATURES is sorted.
@@ -126,6 +127,8 @@ foreach(feature IN LISTS ALL_COMPILER_FEATURES)
       set(LIBC_COMPILER_HAS_BUILTIN_ROUND TRUE)
     elseif(${feature} STREQUAL "builtin_roundeven")
       set(LIBC_COMPILER_HAS_BUILTIN_ROUNDEVEN TRUE)
+    elseif(${feature} STREQUAL "ext_vector_type")
+      set(LIBC_COMPILER_HAS_EXT_VECTOR_TYPE TRUE)
     endif()
   endif()
 endforeach()
diff --git a/libc/cmake/modules/compiler_features/check_ext_vector_type.cpp b/libc/cmake/modules/compiler_features/check_ext_vector_type.cpp
new file mode 100644
index 0000000000000..f268a8ff540f2
--- /dev/null
+++ b/libc/cmake/modules/compiler_features/check_ext_vector_type.cpp
@@ -0,0 +1,7 @@
+#include "src/__support/macros/attributes.h"
+
+#if !LIBC_HAS_VECTOR_TYPE
+#error unsupported
+#endif
+
+bool [[clang::ext_vector_type(1)]] v;
diff --git a/libc/test/src/__support/CPP/CMakeLists.txt b/libc/test/src/__support/CPP/CMakeLists.txt
index 3e1379d812c37..70965d6055bbe 100644
--- a/libc/test/src/__support/CPP/CMakeLists.txt
+++ b/libc/test/src/__support/CPP/CMakeLists.txt
@@ -160,3 +160,15 @@ add_libc_test(
   DEPENDS
   libc.src.__support.CPP.type_traits
 )
+
+if(LIBC_COMPILER_HAS_EXT_VECTOR_TYPE)
+  add_libc_test(
+    simd_test
+    SUITE
+      libc-cpp-utils-tests
+    SRCS
+      simd_test.cpp
+    DEPENDS
+      libc.src.__support.CPP.simd
+  )
+endif()
diff --git a/libc/test/src/__support/CPP/simd_test.cpp b/libc/test/src/__support/CPP/simd_test.cpp
new file mode 100644
index 0000000000000..69324cc913986
--- /dev/null
+++ b/libc/test/src/__support/CPP/simd_test.cpp
@@ -0,0 +1,70 @@
+//===-- Unittests for cpp::simd -------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/__support/CPP/simd.h"
+#include "src/__support/CPP/utility.h"
+
+#include "test/UnitTest/FPMatcher.h"
+#include "test/UnitTest/Test.h"
+
+static_assert(LIBC_HAS_VECTOR_TYPE, "compiler needs ext_vector_type support");
+
+using namespace LIBC_NAMESPACE::cpp;
+
+TEST(LlvmLibcSIMDTest, Basic) {}
+TEST(LlvmLibcSIMDTest, VectorCreation) {
+  simd<int> v1 = splat(5);
+  simd<int> v2 = iota<int>();
+
+  EXPECT_EQ(v1[0], 5);
+  EXPECT_EQ(v2[0], 0);
+}
+
+TEST(LlvmLibcSIMDTest, TypeTraits) {
+  simd<int> v1 = splat(0);
+
+  static_assert(is_simd_v<decltype(v1)>, "v1 should be a SIMD type");
+  static_assert(!is_simd_v<int>, "int is not a SIMD type");
+  static_assert(is_simd_mask_v<simd<bool, 4>>, "should be a SIMD mask");
+
+  using Elem = simd_element_type_t<decltype(v1)>;
+  static_assert(is_same_v<Elem, int>, "element type should be int");
+}
+
+TEST(LlvmLibcSIMDTest, ElementwiseOperations) {
+  simd<int> v1 = splat(1);
+  simd<int> v2 = splat(-1);
+
+  simd<int> v_abs = abs(v2);
+  simd<int> v_min = min(v1, v2);
+  simd<int> v_max = max(v1, v2);
+
+  EXPECT_EQ(v_min[0], -1);
+  EXPECT_EQ(v_max[0], 1);
+  EXPECT_EQ(v_abs[0], 1);
+}
+
+TEST(LlvmLibcSIMDTest, ReductionOperations) {
+  simd<int> v = splat(1);
+
+  int sum = reduce(v);
+  int prod = reduce(v, multiplies<>{});
+
+  EXPECT_EQ(sum, static_cast<int>(simd_size_v<decltype(v)>));
+  EXPECT_EQ(prod, 1); // 1*3*5*7
+}
+
+TEST(LlvmLibcSIMDTest, MaskOperations) {
+  simd<bool, 4> mask{true, false, true, false};
+
+  EXPECT_TRUE(any_of(mask));
+  EXPECT_FALSE(all_of(mask));
+  EXPECT_TRUE(some_of(mask));
+  EXPECT_EQ(find_first_set(mask), 0);
+  EXPECT_EQ(find_last_set(mask), 2);
+}

``````````

</details>


https://github.com/llvm/llvm-project/pull/157746


More information about the libc-commits mailing list