libstdc++-v3/ChangeLog:
* include/bits/simd_alg.h: New file.
Signed-off-by: Matthias Kretz <[email protected]>
---
libstdc++-v3/include/bits/simd_alg.h | 76 ++++++++++++++++++++++++++++
1 file changed, 76 insertions(+)
create mode 100644 libstdc++-v3/include/bits/simd_alg.h
--
──────────────────────────────────────────────────────────────────────────
Dr. Matthias Kretz https://mattkretz.github.io
GSI Helmholtz Center for Heavy Ion Research https://gsi.de
std::simd
──────────────────────────────────────────────────────────────────────────diff --git a/libstdc++-v3/include/bits/simd_alg.h b/libstdc++-v3/include/bits/simd_alg.h
new file mode 100644
index 00000000000..3e9652bae94
--- /dev/null
+++ b/libstdc++-v3/include/bits/simd_alg.h
@@ -0,0 +1,76 @@
+/* SPDX-License-Identifier: GPL-3.0-or-later WITH GCC-exception-3.1 */
+/* Copyright © 2025 GSI Helmholtzzentrum fuer Schwerionenforschung GmbH
+ * Matthias Kretz <[email protected]>
+ */
+
+#ifndef _GLIBCXX_SIMD_ALG_H
+#define _GLIBCXX_SIMD_ALG_H 1
+
+#ifdef _GLIBCXX_SYSHDR
+#pragma GCC system_header
+#endif
+
+#if __cplusplus >= 202400L
+
+#include "simd_vec.h"
+
+// psabi warnings are bogus because the ABI of the internal types never leaks into user code
+#pragma GCC diagnostic push
+#pragma GCC diagnostic ignored "-Wpsabi"
+
+// [simd.alg] -----------------------------------------------------------------
+namespace std::simd
+{
+ template<typename _Tp, typename _Ap>
+ [[__gnu__::__always_inline__]]
+ constexpr basic_vec<_Tp, _Ap>
+ min(const basic_vec<_Tp, _Ap>& __a, const basic_vec<_Tp, _Ap>& __b) noexcept
+ { return __select_impl(__a < __b, __a, __b); }
+
+ template<typename _Tp, typename _Ap>
+ [[__gnu__::__always_inline__]]
+ constexpr basic_vec<_Tp, _Ap>
+ max(const basic_vec<_Tp, _Ap>& __a, const basic_vec<_Tp, _Ap>& __b) noexcept
+ { return __select_impl(__a < __b, __b, __a); }
+
+ template<typename _Tp, typename _Ap>
+ [[__gnu__::__always_inline__]]
+ constexpr pair<basic_vec<_Tp, _Ap>, basic_vec<_Tp, _Ap>>
+ minmax(const basic_vec<_Tp, _Ap>& __a, const basic_vec<_Tp, _Ap>& __b) noexcept
+ { return {min(__a, __b), max(__a, __b)}; }
+
+ template<typename _Tp, typename _Ap>
+ [[__gnu__::__always_inline__]]
+ constexpr basic_vec<_Tp, _Ap>
+ clamp(const basic_vec<_Tp, _Ap>& __v, const basic_vec<_Tp, _Ap>& __lo,
+ const basic_vec<_Tp, _Ap>& __hi)
+ {
+ __glibcxx_simd_precondition(none_of(__lo > __hi), "lower bound is larger than upper bound");
+ return max(__lo, min(__hi, __v));
+ }
+
+ template<typename _Tp, typename _Up>
+ constexpr auto
+ select(bool __c, const _Tp& __a, const _Up& __b)
+ -> remove_cvref_t<decltype(__c ? __a : __b)>
+ { return __c ? __a : __b; }
+
+ template<size_t _Bytes, typename _Ap, typename _Tp, typename _Up>
+ [[__gnu__::__always_inline__]]
+ constexpr auto
+ select(const basic_mask<_Bytes, _Ap>& __c, const _Tp& __a, const _Up& __b)
+ noexcept -> decltype(__select_impl(__c, __a, __b))
+ { return __select_impl(__c, __a, __b); }
+}
+
+namespace std
+{
+ using simd::min;
+ using simd::max;
+ using simd::minmax;
+ using simd::clamp;
+}
+
+#pragma GCC diagnostic pop
+#endif // C++26
+#endif // _GLIBCXX_SIMD_ALG_H