11
11
#include " CL/sycl/ONEAPI/accessor_property_list.hpp"
12
12
#include < CL/sycl/ONEAPI/group_algorithm.hpp>
13
13
#include < CL/sycl/accessor.hpp>
14
+ #include < CL/sycl/atomic.hpp>
14
15
#include < CL/sycl/handler.hpp>
15
16
#include < CL/sycl/kernel.hpp>
16
17
@@ -22,121 +23,103 @@ namespace ONEAPI {
22
23
23
24
namespace detail {
24
25
26
+ using cl::sycl::detail::bool_constant;
27
+ using cl::sycl::detail::enable_if_t ;
28
+ using cl::sycl::detail::is_sgenfloat;
29
+ using cl::sycl::detail::is_sgeninteger;
25
30
using cl::sycl::detail::queue_impl;
31
+ using cl::sycl::detail::remove_AS;
26
32
27
33
__SYCL_EXPORT size_t reduGetMaxWGSize (shared_ptr_class<queue_impl> Queue,
28
34
size_t LocalMemBytesPerWorkItem);
29
35
__SYCL_EXPORT size_t reduComputeWGSize (size_t NWorkItems, size_t MaxWGSize,
30
36
size_t &NWorkGroups);
31
37
32
- using cl::sycl::detail::bool_constant;
33
- using cl::sycl::detail::enable_if_t ;
34
- using cl::sycl::detail::is_geninteger16bit;
35
- using cl::sycl::detail::is_geninteger32bit;
36
- using cl::sycl::detail::is_geninteger64bit;
37
- using cl::sycl::detail::is_geninteger8bit;
38
- using cl::sycl::detail::remove_AS;
39
-
40
38
template <typename T, class BinaryOperation >
41
- using IsReduPlus = detail::bool_constant<
42
- std::is_same<BinaryOperation, ONEAPI::plus<T>>::value ||
43
- std::is_same<BinaryOperation, ONEAPI::plus<void >>::value>;
39
+ using IsReduPlus =
40
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::plus<T>>::value ||
41
+ std::is_same<BinaryOperation, ONEAPI::plus<void >>::value>;
44
42
45
43
template <typename T, class BinaryOperation >
46
- using IsReduMultiplies = detail::bool_constant<
47
- std::is_same<BinaryOperation, std::multiplies<T>>::value ||
48
- std::is_same<BinaryOperation, std::multiplies<void >>::value>;
44
+ using IsReduMultiplies =
45
+ bool_constant< std::is_same<BinaryOperation, std::multiplies<T>>::value ||
46
+ std::is_same<BinaryOperation, std::multiplies<void >>::value>;
49
47
50
48
template <typename T, class BinaryOperation >
51
- using IsReduMinimum = detail::bool_constant<
52
- std::is_same<BinaryOperation, ONEAPI::minimum<T>>::value ||
53
- std::is_same<BinaryOperation, ONEAPI::minimum<void >>::value>;
49
+ using IsReduMinimum =
50
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::minimum<T>>::value ||
51
+ std::is_same<BinaryOperation, ONEAPI::minimum<void >>::value>;
54
52
55
53
template <typename T, class BinaryOperation >
56
- using IsReduMaximum = detail::bool_constant<
57
- std::is_same<BinaryOperation, ONEAPI::maximum<T>>::value ||
58
- std::is_same<BinaryOperation, ONEAPI::maximum<void >>::value>;
54
+ using IsReduMaximum =
55
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::maximum<T>>::value ||
56
+ std::is_same<BinaryOperation, ONEAPI::maximum<void >>::value>;
59
57
60
58
template <typename T, class BinaryOperation >
61
- using IsReduBitOR = detail::bool_constant<
62
- std::is_same<BinaryOperation, ONEAPI::bit_or<T>>::value ||
63
- std::is_same<BinaryOperation, ONEAPI::bit_or<void >>::value>;
59
+ using IsReduBitOR =
60
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::bit_or<T>>::value ||
61
+ std::is_same<BinaryOperation, ONEAPI::bit_or<void >>::value>;
64
62
65
63
template <typename T, class BinaryOperation >
66
- using IsReduBitXOR = detail::bool_constant<
67
- std::is_same<BinaryOperation, ONEAPI::bit_xor<T>>::value ||
68
- std::is_same<BinaryOperation, ONEAPI::bit_xor<void >>::value>;
64
+ using IsReduBitXOR =
65
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::bit_xor<T>>::value ||
66
+ std::is_same<BinaryOperation, ONEAPI::bit_xor<void >>::value>;
69
67
70
68
template <typename T, class BinaryOperation >
71
- using IsReduBitAND = detail::bool_constant<
72
- std::is_same<BinaryOperation, ONEAPI::bit_and<T>>::value ||
73
- std::is_same<BinaryOperation, ONEAPI::bit_and<void >>::value>;
69
+ using IsReduBitAND =
70
+ bool_constant< std::is_same<BinaryOperation, ONEAPI::bit_and<T>>::value ||
71
+ std::is_same<BinaryOperation, ONEAPI::bit_and<void >>::value>;
74
72
75
73
template <typename T, class BinaryOperation >
76
74
using IsReduOptForFastAtomicFetch =
77
- detail:: bool_constant<(is_geninteger32bit <T>::value ||
78
- is_geninteger64bit <T>::value) &&
79
- (IsReduPlus<T, BinaryOperation>::value ||
80
- IsReduMinimum<T, BinaryOperation>::value ||
81
- IsReduMaximum<T, BinaryOperation>::value ||
82
- IsReduBitOR<T, BinaryOperation>::value ||
83
- IsReduBitXOR<T, BinaryOperation>::value ||
84
- IsReduBitAND<T, BinaryOperation>::value)>;
75
+ bool_constant<is_sgeninteger <T>::value &&
76
+ sycl::detail::IsValidAtomicType <T>::value &&
77
+ (IsReduPlus<T, BinaryOperation>::value ||
78
+ IsReduMinimum<T, BinaryOperation>::value ||
79
+ IsReduMaximum<T, BinaryOperation>::value ||
80
+ IsReduBitOR<T, BinaryOperation>::value ||
81
+ IsReduBitXOR<T, BinaryOperation>::value ||
82
+ IsReduBitAND<T, BinaryOperation>::value)>;
85
83
86
84
template <typename T, class BinaryOperation >
87
- using IsReduOptForFastReduce = detail::bool_constant<
88
- (is_geninteger32bit <T>::value || is_geninteger64bit<T>::value ||
89
- std::is_same<T, half>::value || std::is_same<T, float >::value ||
90
- std::is_same<T, double >::value) &&
91
- (IsReduPlus<T, BinaryOperation>::value ||
92
- IsReduMinimum<T, BinaryOperation>::value ||
93
- IsReduMaximum<T, BinaryOperation>::value)>;
85
+ using IsReduOptForFastReduce =
86
+ bool_constant<((is_sgeninteger <T>::value &&
87
+ ( sizeof (T) == 32 || sizeof (T) == 64 )) ||
88
+ is_sgenfloat<T >::value) &&
89
+ (IsReduPlus<T, BinaryOperation>::value ||
90
+ IsReduMinimum<T, BinaryOperation>::value ||
91
+ IsReduMaximum<T, BinaryOperation>::value)>;
94
92
95
93
// Identity = 0
96
94
template <typename T, class BinaryOperation >
97
95
using IsZeroIdentityOp = bool_constant<
98
- ((is_geninteger8bit<T>::value || is_geninteger16bit<T>::value ||
99
- is_geninteger32bit<T>::value || is_geninteger64bit<T>::value) &&
100
- (IsReduPlus<T, BinaryOperation>::value ||
101
- IsReduBitOR<T, BinaryOperation>::value ||
102
- IsReduBitXOR<T, BinaryOperation>::value)) ||
103
- ((std::is_same<T, half>::value || std::is_same<T, float >::value ||
104
- std::is_same<T, double >::value) &&
105
- IsReduPlus<T, BinaryOperation>::value)>;
96
+ (is_sgeninteger<T>::value && (IsReduPlus<T, BinaryOperation>::value ||
97
+ IsReduBitOR<T, BinaryOperation>::value ||
98
+ IsReduBitXOR<T, BinaryOperation>::value)) ||
99
+ (is_sgenfloat<T>::value && IsReduPlus<T, BinaryOperation>::value)>;
106
100
107
101
// Identity = 1
108
102
template <typename T, class BinaryOperation >
109
- using IsOneIdentityOp = bool_constant<
110
- (is_geninteger8bit<T>::value || is_geninteger16bit<T>::value ||
111
- is_geninteger32bit<T>::value || is_geninteger64bit<T>::value ||
112
- std::is_same<T, half>::value || std::is_same<T, float >::value ||
113
- std::is_same<T, double >::value) &&
114
- IsReduMultiplies<T, BinaryOperation>::value>;
103
+ using IsOneIdentityOp =
104
+ bool_constant<(is_sgeninteger<T>::value || is_sgenfloat<T>::value) &&
105
+ IsReduMultiplies<T, BinaryOperation>::value>;
115
106
116
107
// Identity = ~0
117
108
template <typename T, class BinaryOperation >
118
- using IsOnesIdentityOp = bool_constant<
119
- (is_geninteger8bit<T>::value || is_geninteger16bit<T>::value ||
120
- is_geninteger32bit<T>::value || is_geninteger64bit<T>::value) &&
121
- IsReduBitAND<T, BinaryOperation>::value>;
109
+ using IsOnesIdentityOp = bool_constant<is_sgeninteger<T>::value &&
110
+ IsReduBitAND<T, BinaryOperation>::value>;
122
111
123
112
// Identity = <max possible value>
124
113
template <typename T, class BinaryOperation >
125
- using IsMinimumIdentityOp = bool_constant<
126
- (is_geninteger8bit<T>::value || is_geninteger16bit<T>::value ||
127
- is_geninteger32bit<T>::value || is_geninteger64bit<T>::value ||
128
- std::is_same<T, half>::value || std::is_same<T, float >::value ||
129
- std::is_same<T, double >::value) &&
130
- IsReduMinimum<T, BinaryOperation>::value>;
114
+ using IsMinimumIdentityOp =
115
+ bool_constant<(is_sgeninteger<T>::value || is_sgenfloat<T>::value) &&
116
+ IsReduMinimum<T, BinaryOperation>::value>;
131
117
132
118
// Identity = <min possible value>
133
119
template <typename T, class BinaryOperation >
134
- using IsMaximumIdentityOp = bool_constant<
135
- (is_geninteger8bit<T>::value || is_geninteger16bit<T>::value ||
136
- is_geninteger32bit<T>::value || is_geninteger64bit<T>::value ||
137
- std::is_same<T, half>::value || std::is_same<T, float >::value ||
138
- std::is_same<T, double >::value) &&
139
- IsReduMaximum<T, BinaryOperation>::value>;
120
+ using IsMaximumIdentityOp =
121
+ bool_constant<(is_sgeninteger<T>::value || is_sgenfloat<T>::value) &&
122
+ IsReduMaximum<T, BinaryOperation>::value>;
140
123
141
124
template <typename T, class BinaryOperation >
142
125
using IsKnownIdentityOp =
@@ -343,7 +326,7 @@ class reducer<T, BinaryOperation,
343
326
// / Atomic ADD operation: *ReduVarPtr += MValue;
344
327
template <typename _T = T, class _BinaryOperation = BinaryOperation>
345
328
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
346
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
329
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
347
330
IsReduPlus<T, _BinaryOperation>::value>
348
331
atomic_combine (_T *ReduVarPtr) const {
349
332
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -353,7 +336,7 @@ class reducer<T, BinaryOperation,
353
336
// / Atomic BITWISE OR operation: *ReduVarPtr |= MValue;
354
337
template <typename _T = T, class _BinaryOperation = BinaryOperation>
355
338
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
356
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
339
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
357
340
IsReduBitOR<T, _BinaryOperation>::value>
358
341
atomic_combine (_T *ReduVarPtr) const {
359
342
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -363,7 +346,7 @@ class reducer<T, BinaryOperation,
363
346
// / Atomic BITWISE XOR operation: *ReduVarPtr ^= MValue;
364
347
template <typename _T = T, class _BinaryOperation = BinaryOperation>
365
348
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
366
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
349
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
367
350
IsReduBitXOR<T, _BinaryOperation>::value>
368
351
atomic_combine (_T *ReduVarPtr) const {
369
352
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -373,7 +356,7 @@ class reducer<T, BinaryOperation,
373
356
// / Atomic BITWISE AND operation: *ReduVarPtr &= MValue;
374
357
template <typename _T = T, class _BinaryOperation = BinaryOperation>
375
358
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
376
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
359
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
377
360
IsReduBitAND<T, _BinaryOperation>::value>
378
361
atomic_combine (_T *ReduVarPtr) const {
379
362
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -383,7 +366,7 @@ class reducer<T, BinaryOperation,
383
366
// / Atomic MIN operation: *ReduVarPtr = ONEAPI::minimum(*ReduVarPtr, MValue);
384
367
template <typename _T = T, class _BinaryOperation = BinaryOperation>
385
368
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
386
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
369
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
387
370
IsReduMinimum<T, _BinaryOperation>::value>
388
371
atomic_combine (_T *ReduVarPtr) const {
389
372
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -393,7 +376,7 @@ class reducer<T, BinaryOperation,
393
376
// / Atomic MAX operation: *ReduVarPtr = ONEAPI::maximum(*ReduVarPtr, MValue);
394
377
template <typename _T = T, class _BinaryOperation = BinaryOperation>
395
378
enable_if_t <std::is_same<typename remove_AS<_T>::type, T>::value &&
396
- (is_geninteger32bit<T>::value || is_geninteger64bit<T >::value) &&
379
+ IsReduOptForFastAtomicFetch<T, _BinaryOperation >::value &&
397
380
IsReduMaximum<T, _BinaryOperation>::value>
398
381
atomic_combine (_T *ReduVarPtr) const {
399
382
atomic<T, access::address_space::global_space>(global_ptr<T>(ReduVarPtr))
@@ -1604,7 +1587,7 @@ reduction(accessor<T, Dims, AccMode, access::target::global_buffer, IsPH> &Acc,
1604
1587
// / The identity value is not passed to this version as it is statically known.
1605
1588
template <typename T, class BinaryOperation , int Dims, access::mode AccMode,
1606
1589
access::placeholder IsPH>
1607
- detail ::enable_if_t <
1590
+ std ::enable_if_t <
1608
1591
detail::IsKnownIdentityOp<T, BinaryOperation>::value,
1609
1592
detail::reduction_impl<T, BinaryOperation, Dims, false , AccMode, IsPH>>
1610
1593
reduction (accessor<T, Dims, AccMode, access::target::global_buffer, IsPH> &Acc,
@@ -1632,9 +1615,9 @@ reduction(T *VarPtr, const T &Identity, BinaryOperation BOp) {
1632
1615
// / operation used in the reduction.
1633
1616
// / The identity value is not passed to this version as it is statically known.
1634
1617
template <typename T, class BinaryOperation >
1635
- detail ::enable_if_t <detail::IsKnownIdentityOp<T, BinaryOperation>::value,
1636
- detail::reduction_impl<T, BinaryOperation, 0 , true ,
1637
- access::mode::read_write>>
1618
+ std ::enable_if_t <detail::IsKnownIdentityOp<T, BinaryOperation>::value,
1619
+ detail::reduction_impl<T, BinaryOperation, 0 , true ,
1620
+ access::mode::read_write>>
1638
1621
reduction (T *VarPtr, BinaryOperation) {
1639
1622
return detail::reduction_impl<T, BinaryOperation, 0 , true ,
1640
1623
access::mode::read_write>(VarPtr);
@@ -1659,7 +1642,30 @@ template <typename BinaryOperation, typename AccumulatorT>
1659
1642
inline constexpr AccumulatorT known_identity_v =
1660
1643
known_identity<BinaryOperation, AccumulatorT>::value;
1661
1644
#endif
1662
-
1663
1645
} // namespace ONEAPI
1646
+
1647
+ // Currently, the type traits defined below correspond to SYCL 1.2.1 ONEAPI
1648
+ // reduction extension. That may be changed later when SYCL 2020 reductions
1649
+ // are implemented.
1650
+ template <typename BinaryOperation, typename AccumulatorT>
1651
+ struct has_known_identity
1652
+ : ONEAPI::has_known_identity<BinaryOperation, AccumulatorT> {};
1653
+
1654
+ #if __cplusplus >= 201703L
1655
+ template <typename BinaryOperation, typename AccumulatorT>
1656
+ inline constexpr bool has_known_identity_v =
1657
+ has_known_identity<BinaryOperation, AccumulatorT>::value;
1658
+ #endif
1659
+
1660
+ template <typename BinaryOperation, typename AccumulatorT>
1661
+ struct known_identity : ONEAPI::known_identity<BinaryOperation, AccumulatorT> {
1662
+ };
1663
+
1664
+ #if __cplusplus >= 201703L
1665
+ template <typename BinaryOperation, typename AccumulatorT>
1666
+ inline constexpr AccumulatorT known_identity_v =
1667
+ known_identity<BinaryOperation, AccumulatorT>::value;
1668
+ #endif
1669
+
1664
1670
} // namespace sycl
1665
1671
} // __SYCL_INLINE_NAMESPACE(cl)
0 commit comments