Vc 1.4.5
SIMD Vector Classes for C++
 
Loading...
Searching...
No Matches
types.h
1/* This file is part of the Vc library. {{{
2Copyright © 2012-2015 Matthias Kretz <kretz@kde.org>
3
4Redistribution and use in source and binary forms, with or without
5modification, are permitted provided that the following conditions are met:
6 * Redistributions of source code must retain the above copyright
7 notice, this list of conditions and the following disclaimer.
8 * Redistributions in binary form must reproduce the above copyright
9 notice, this list of conditions and the following disclaimer in the
10 documentation and/or other materials provided with the distribution.
11 * Neither the names of contributing organizations nor the
12 names of its contributors may be used to endorse or promote products
13 derived from this software without specific prior written permission.
14
15THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
16ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
19DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
22ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25
26}}}*/
27
28#ifndef VC_COMMON_TYPES_H_
29#define VC_COMMON_TYPES_H_
30
31#ifdef Vc_CHECK_ALIGNMENT
32#include <cstdlib>
33#include <cstdio>
34#endif
35
36#include <ratio>
37#include "../global.h"
38#include "../traits/type_traits.h"
39#include "permutation.h"
40
41namespace Vc_VERSIONED_NAMESPACE
42{
45
47using std::size_t;
48
50using llong = long long;
52using ullong = unsigned long long;
54using ulong = unsigned long;
56using uint = unsigned int;
58using ushort = unsigned short;
60using uchar = unsigned char;
62using schar = signed char;
63
67struct VectorSpecialInitializerZero {};
71struct VectorSpecialInitializerOne {};
75struct VectorSpecialInitializerIndexesFromZero {};
76
81constexpr VectorSpecialInitializerZero Zero = {};
86constexpr VectorSpecialInitializerOne One = {};
91constexpr VectorSpecialInitializerIndexesFromZero IndexesFromZero = {};
93
94namespace Detail
95{
96template<typename T> struct MayAliasImpl {
97#ifdef Vc_ICC
98#pragma warning(disable:2621)
99#endif
100#ifdef __GNUC__
101#pragma GCC diagnostic push
102#pragma GCC diagnostic ignored "-Wattributes"
103#endif
104 typedef T type Vc_MAY_ALIAS;
105#ifdef __GNUC__
106#pragma GCC diagnostic pop
107#endif
108#ifdef Vc_ICC
109#pragma warning(enable:2621)
110#endif
111};
112//template<size_t Bytes> struct MayAlias<MaskBool<Bytes>> { typedef MaskBool<Bytes> type; };
113} // namespace Detail
120template <typename T> using MayAlias = typename Detail::MayAliasImpl<T>::type;
121
122template <class To, class From> MayAlias<To> &aliasing_cast(From &x)
123{
124 return *reinterpret_cast<MayAlias<To> *>(&x);
125}
126template <class To, class From> const MayAlias<To> &aliasing_cast(const From &x)
127{
128 return *reinterpret_cast<const MayAlias<To> *>(&x);
129}
130
131template <class To, class From> MayAlias<To> *aliasing_cast(From *x)
132{
133 return reinterpret_cast<MayAlias<To> *>(x);
134}
135template <class To, class From> const MayAlias<To> *aliasing_cast(const From *x)
136{
137 return reinterpret_cast<const MayAlias<To> *>(x);
138}
139
146enum class Operator : char {
147 Assign,
148 Multiply,
149 MultiplyAssign,
150 Divide,
151 DivideAssign,
152 Remainder,
153 RemainderAssign,
154 Plus,
155 PlusAssign,
156 Minus,
157 MinusAssign,
158 RightShift,
159 RightShiftAssign,
160 LeftShift,
161 LeftShiftAssign,
162 And,
163 AndAssign,
164 Xor,
165 XorAssign,
166 Or,
167 OrAssign,
168 PreIncrement,
169 PostIncrement,
170 PreDecrement,
171 PostDecrement,
172 LogicalAnd,
173 LogicalOr,
174 Comma,
175 UnaryPlus,
176 UnaryMinus,
177 UnaryNot,
178 UnaryOnesComplement,
179 CompareEqual,
180 CompareNotEqual,
181 CompareLess,
182 CompareGreater,
183 CompareLessEqual,
184 CompareGreaterEqual
185};
186
187// forward declaration for Vc::array in <Vc/array>
188template <typename T, std::size_t N> struct array;
189// forward declaration for Vc::span in <Vc/span>
190namespace Common {
191template <typename T, std::ptrdiff_t N> class span;
192}
193
194/* TODO: add type for half-float, something along these lines:
195class half_float
196{
197 uint16_t data;
198public:
199 constexpr half_float() : data(0) {}
200 constexpr half_float(const half_float &) = default;
201 constexpr half_float(half_float &&) = default;
202 constexpr half_float &operator=(const half_float &) = default;
203
204 constexpr explicit half_float(float);
205 constexpr explicit half_float(double);
206 constexpr explicit half_float(int);
207 constexpr explicit half_float(unsigned int);
208
209 explicit operator float () const;
210 explicit operator double () const;
211 explicit operator int () const;
212 explicit operator unsigned int() const;
213
214 bool operator==(half_float rhs) const;
215 bool operator!=(half_float rhs) const;
216 bool operator>=(half_float rhs) const;
217 bool operator<=(half_float rhs) const;
218 bool operator> (half_float rhs) const;
219 bool operator< (half_float rhs) const;
220
221 half_float operator+(half_float rhs) const;
222 half_float operator-(half_float rhs) const;
223 half_float operator*(half_float rhs) const;
224 half_float operator/(half_float rhs) const;
225};
226*/
227
228// TODO: the following doesn't really belong into the toplevel Vc namespace.
229#ifndef Vc_CHECK_ALIGNMENT
230template<typename _T> static Vc_ALWAYS_INLINE void assertCorrectAlignment(const _T *){}
231#else
232template<typename _T> static Vc_ALWAYS_INLINE void assertCorrectAlignment(const _T *ptr)
233{
234 const size_t s = alignof(_T);
235 if((reinterpret_cast<size_t>(ptr) & ((s ^ (s & (s - 1))) - 1)) != 0) {
236 fprintf(stderr, "A vector with incorrect alignment has just been created. Look at the stacktrace to find the guilty object.\n");
237 abort();
238 }
239}
240#endif
241
242namespace Common
243{
244// defined in common/simdarrayhelper.h
245template <typename T, std::size_t Pieces, std::size_t Index> struct Segment;
246
253template<size_t StructSize> class SuccessiveEntries
254{
255#ifdef Vc_MSVC
256 // scatterinterleavedmemory fails with garbage values in m_first if size_type is a
257 // 64-bit integer type. Using a 32-bit type seems to work around the miscompilation.
258 using size_type = unsigned;
259#else
260 using size_type = size_t;
261#endif
262 const size_type m_first;
263
264public:
265 typedef SuccessiveEntries AsArg;
266 Vc_INTRINSIC SuccessiveEntries(size_type first) : m_first(first) {}
267 Vc_INTRINSIC Vc_PURE size_type operator[](size_type offset) const
268 {
269 return m_first + offset * StructSize;
270 }
271 Vc_INTRINSIC Vc_PURE size_type data() const { return m_first; }
272 Vc_INTRINSIC Vc_PURE SuccessiveEntries operator+(const SuccessiveEntries &rhs) const
273 {
274 return SuccessiveEntries(m_first + rhs.m_first);
275 }
276 Vc_INTRINSIC Vc_PURE SuccessiveEntries operator*(const SuccessiveEntries &rhs) const
277 {
278 return SuccessiveEntries(m_first * rhs.m_first);
279 }
280 Vc_INTRINSIC Vc_PURE SuccessiveEntries operator<<(size_type x) const
281 {
282 return {m_first << x};
283 }
284
285 friend Vc_INTRINSIC SuccessiveEntries &internal_data(SuccessiveEntries &x)
286 {
287 return x;
288 }
289 friend Vc_INTRINSIC const SuccessiveEntries &internal_data(const SuccessiveEntries &x)
290 {
291 return x;
292 }
293};
294
295// declaration for functions in common/malloc.h
296template <std::size_t alignment>
297Vc_INTRINSIC_L void *aligned_malloc(std::size_t n) Vc_INTRINSIC_R;
298Vc_ALWAYS_INLINE_L void free(void *p) Vc_ALWAYS_INLINE_R;
299
303template <typename Mask, typename T, typename U>
304using enable_if_mask_converts_implicitly =
305 enable_if<(!std::is_same<Mask, Traits::decay<U>>::value && // that'd be the copy ctor
306 Traits::is_simd_mask<U>::value && !Traits::isSimdMaskArray<U>::value &&
307 Traits::is_implicit_cast_allowed_mask<
308 Traits::entry_type_of<typename Traits::decay<U>::Vector>, T>::value)>;
312template <typename T, typename U>
313using enable_if_mask_converts_explicitly = enable_if<(
314 Traits::isSimdMaskArray<U>::value ||
315 (Traits::is_simd_mask<U>::value &&
316 !Traits::is_implicit_cast_allowed_mask<
317 Traits::entry_type_of<typename Traits::decay<U>::Vector>, T>::value))>;
318
322template <typename T> using WidthT = std::integral_constant<std::size_t, sizeof(T)>;
323
324// forward declaration of MaskBool in common/maskbool.h
325template <std::size_t Bytes> class MaskBool;
326
327// forward declaration of SubscriptOperation in common/subscript.h
328template <typename T, typename IndexVector, typename Scale, bool>
329class SubscriptOperation;
330
338template <class T, class IndexVector, int Scale = 1>
339struct GatherArguments {
340 static_assert(std::is_same<T, remove_cvref_t<T>>::value && !std::is_pointer<T>::value,
341 "GatherArguments expects an cv unqualified non-ref/ptr type");
342 const IndexVector indexes;
343 const T *const address;
344};
345template <int Scale, class T, class I>
346GatherArguments<T, I, Scale> make_gather(const T *m, const I &i)
347{
348 return {i, m};
349}
350
358template <typename T, typename IndexVector> struct ScatterArguments
359{
360 const IndexVector indexes;
361 T *const address;
362};
363
367template <typename I, I Begin, I End, typename F>
368Vc_INTRINSIC enable_if<(Begin >= End), void> unrolled_loop(F &&)
369{
370}
371
377template <typename I, I Begin, I End, typename F>
378Vc_INTRINSIC Vc_FLATTEN enable_if<(Begin < End), void> unrolled_loop(F &&f)
379{
380 f(Begin);
381 unrolled_loop<I, Begin + 1, End>(f);
382}
383
388template <std::size_t Size, typename F> Vc_INTRINSIC void for_all_vector_entries(F &&f)
389{
390 unrolled_loop<std::size_t, 0u, Size>(std::forward<F>(f));
391}
392
393} // namespace Common
394} // namespace Vc
395
396#include "vector.h"
397#include "mask.h"
398#include "memoryfwd.h"
399
400#endif // VC_COMMON_TYPES_H_
401
402// vim: foldmethod=marker
Common::AdaptSubscriptOperator< Common::span< T, Extent > > span
An adapted std::span with additional subscript operators supporting gather and scatter operations.
Definition span.h:639
constexpr VectorSpecialInitializerIndexesFromZero IndexesFromZero
The special object Vc::IndexesFromZero can be used to construct Vector objects initialized to values ...
Definition types.h:91
unsigned long long ullong
unsigned long long shorthand
Definition types.h:52
unsigned long ulong
unsigned long shorthand
Definition types.h:54
long long llong
long long shorthand
Definition types.h:50
unsigned int uint
unsigned int shorthand
Definition types.h:56
constexpr VectorSpecialInitializerOne One
The special object Vc::One can be used to construct Vector and Mask objects initialized to one/true.
Definition types.h:86
signed char schar
signed char shorthand
Definition types.h:62
constexpr VectorSpecialInitializerZero Zero
The special object Vc::Zero can be used to construct Vector and Mask objects initialized to zero/fals...
Definition types.h:81
unsigned char uchar
unsigned char shorthand
Definition types.h:60
unsigned short ushort
unsigned short shorthand
Definition types.h:58
This is std::array with additional subscript operators supporting gather and scatter operations.
Definition types.h:188