SeqAn3 3.3.0-rc.1
The Modern C++ library for sequence analysis.
 
Loading...
Searching...
No Matches
builtin_simd.hpp
Go to the documentation of this file.
1// -----------------------------------------------------------------------------------------------------
2// Copyright (c) 2006-2022, Knut Reinert & Freie Universität Berlin
3// Copyright (c) 2016-2022, Knut Reinert & MPI für molekulare Genetik
4// This file may be used, modified and/or redistributed under the terms of the 3-clause BSD-License
5// shipped with this file and also available at: https://github.com/seqan/seqan3/blob/master/LICENSE.md
6// -----------------------------------------------------------------------------------------------------
7
14#pragma once
15
16#include <bit>
17#include <type_traits>
18
23
24namespace seqan3::detail
25{
26
52template <typename scalar_t, size_t length>
54
57template <typename scalar_t, size_t length>
58 requires (std::has_single_bit(length))
60{
62#if SEQAN3_DOXYGEN_ONLY(1) 0
63 using type = scalar_t __attribute__((vector_size(sizeof(scalar_t) * length))));
64 // doxygen 1.8.13 does not support c++11 attributes, thus this doxygen-only definition
65#elif defined(__clang__)
66 using type = scalar_t __attribute__((ext_vector_type(length)));
67#else
68 using type [[gnu::vector_size(sizeof(scalar_t) * length)]] = scalar_t;
69#endif
70};
71
76template <typename builtin_simd_t>
78{};
79
84template <typename builtin_simd_t>
86// NOTE: gcc throws a compile time error if builtin_simd_t is a pointer of an incomplete type. To tackle this we
87// short-circuit the requires with is_pointer_v. See builtin_simd_test.cpp for a test case for this.
88 requires (!std::is_pointer_v<std::decay_t<builtin_simd_t>>) && requires (builtin_simd_t simd) {
89 {
90 simd[0]
91 };
92 }
94struct builtin_simd_traits_helper<builtin_simd_t>
95{
99 static constexpr auto length = sizeof(builtin_simd_t) / sizeof(scalar_type);
100
103 static constexpr bool value =
104 std::has_single_bit(length)
105 && std::is_same_v<builtin_simd_t, transformation_trait_or_t<builtin_simd<scalar_type, length>, void>>;
106};
107
116template <typename builtin_simd_t>
117struct is_builtin_simd : std::bool_constant<builtin_simd_traits_helper<builtin_simd_t>::value>
118{};
119
125template <typename builtin_simd_t>
127
136template <>
138{
139#if defined(__AVX512F__)
140 return min_viable_uint_v<64u>;
141#elif defined(__AVX2__)
142 return min_viable_uint_v<32u>;
143#elif defined(__SSE4_1__) && defined(__SSE4_2__)
144 return min_viable_uint_v<16u>;
145#else
146 return min_viable_uint_v<0u>;
147#endif
148}();
149
162template <typename builtin_simd_t>
164 std::bool_constant<(default_simd_max_length<builtin_simd> != 0)
165 && ((builtin_simd_traits_helper<builtin_simd_t>::length
166 * sizeof(typename builtin_simd_traits_helper<builtin_simd_t>::scalar_type))
167 >= 16)
168 && ((builtin_simd_traits_helper<builtin_simd_t>::length
169 * sizeof(typename builtin_simd_traits_helper<builtin_simd_t>::scalar_type))
170 <= 64)>
171{};
172
178template <typename builtin_simd_t>
180
181} // namespace seqan3::detail
182
183namespace seqan3
184{
185
186inline namespace simd
187{
188
194template <typename builtin_simd_t>
195// \cond
197// \endcond
198struct simd_traits<builtin_simd_t>
199{
205 static constexpr auto max_length = length == 1u ? length : sizeof(scalar_type) * length;
206
207 static_assert(std::is_integral_v<scalar_type>, "For now we assume that builtin simd can only be integers");
209 using mask_type = decltype(std::declval<builtin_simd_t>() == std::declval<builtin_simd_t>());
212
214 template <typename new_scalar_type>
215 // \cond
216 requires (sizeof(scalar_type) == sizeof(new_scalar_type))
217 // \endcond
219};
220
221} // namespace simd
222
223} // namespace seqan3
Provides seqan3::detail::default_simd_length and seqan3::detail::default_simd_max_length.
constexpr bool is_builtin_simd_v
Helper variable to test whether a type is a simd builtin type.
Definition: builtin_simd.hpp:126
constexpr bool is_native_builtin_simd_v
Helper variable to test whether a type is a native simd builtin type.
Definition: builtin_simd.hpp:179
constexpr auto default_simd_max_length< builtin_simd >
This function specializes seqan3::detail::default_simd_max_length for seqan3::detail::builtin_simd.
Definition: builtin_simd.hpp:137
T has_single_bit(T... args)
Provides metaprogramming utilities for integer types.
The internal SeqAn3 namespace.
Definition: aligned_sequence_concept.hpp:29
The main SeqAn3 namespace.
Definition: aligned_sequence_concept.hpp:29
Provides seqan3::simd::simd_traits.
scalar_t __attribute__((vector_size(sizeof(scalar_t) *length)))) type
The type of the builtin simd.
Definition: builtin_simd.hpp:63
Helper struct for seqan3::detail::is_builtin_simd.
Definition: builtin_simd.hpp:78
A class that holds the type of a simd implementation called [vector extension] (https://gcc....
Definition: builtin_simd.hpp:53
This class inherits from std::true_type, iff seqan3::detail::builtin_simd<scalar_t,...
Definition: builtin_simd.hpp:118
This class inherits from std::true_type, iff the builtin simd type is supported by the current archit...
Definition: builtin_simd.hpp:171
typename detail::builtin_simd< uint8_t, max_length >::type swizzle_type
The type used to define how to swizzle a simd vector (is not defined if simd_t does not model seqan3:...
Definition: builtin_simd.hpp:211
decltype(std::declval< builtin_simd_t >()==std::declval< builtin_simd_t >()) mask_type
The type returned by comparison operators (is not defined if simd_t does not model seqan3::simd::simd...
Definition: builtin_simd.hpp:209
typename detail::builtin_simd< new_scalar_type, length >::type rebind
The type used to rebind a simd vector to another scalar_type (is not defined if simd_t does not model...
Definition: builtin_simd.hpp:218
typename detail::builtin_simd_traits_helper< builtin_simd_t >::scalar_type scalar_type
The underlying type of a simd vector (is not defined if simd_t does not model seqan3::simd::simd)
Definition: builtin_simd.hpp:201
seqan3::simd::simd_traits is the trait class that provides uniform interface to the properties of sim...
Definition: simd_traits.hpp:41
static constexpr auto length
The number of packed values in a simd vector (is not defined if simd_t does not model seqan3::simd::s...
Definition: simd_traits.hpp:49
IMPLEMENTATION_DEFINED scalar_type
The underlying type of a simd vector (is not defined if simd_t does not model seqan3::simd::simd)
Definition: simd_traits.hpp:45
static constexpr auto max_length
The maximum number of packable values in a simd vector, if the underlying type would be [u]int8_t (is...
Definition: simd_traits.hpp:54
Provides seqan3::detail::transformation_trait_or.