diff --git a/include/oneapi/dpl/experimental/kt/internal/esimd_radix_sort_utils.h b/include/oneapi/dpl/experimental/kt/internal/esimd_radix_sort_utils.h index b2a291822c4..7333fd6ac9d 100644 --- a/include/oneapi/dpl/experimental/kt/internal/esimd_radix_sort_utils.h +++ b/include/oneapi/dpl/experimental/kt/internal/esimd_radix_sort_utils.h @@ -219,9 +219,9 @@ __rng_data(const _Rng& __rng) // sycl::accessor::operator[] are supported only with -fsycl-esimd-force-stateless-mem. // Otherwise, all memory accesses through an accessor are done via explicit APIs // TODO: rely on begin() once -fsycl-esimd-force-stateless-mem has been enabled by default -template +template auto -__rng_data(const oneapi::dpl::__ranges::all_view<_T, _M>& __view) +__rng_data(const oneapi::dpl::__ranges::all_view<_T, _M, _NoInit>& __view) { return __view.accessor(); } diff --git a/include/oneapi/dpl/internal/async_impl/async_impl_hetero.h b/include/oneapi/dpl/internal/async_impl/async_impl_hetero.h index da8f4679ed1..dc687f893d5 100644 --- a/include/oneapi/dpl/internal/async_impl/async_impl_hetero.h +++ b/include/oneapi/dpl/internal/async_impl/async_impl_hetero.h @@ -30,8 +30,8 @@ namespace dpl namespace __internal { -template <__par_backend_hetero::access_mode __acc_mode, bool _IsNoInitRequested, typename _BackendTag, - typename _ExecutionPolicy, typename _ForwardIterator, typename _Function> +template <__par_backend_hetero::access_mode __acc_mode, bool _IsNoInitRequested, bool _DeferToUserHint = false, + typename _BackendTag, typename _ExecutionPolicy, typename _ForwardIterator, typename _Function> auto __pattern_walk1_async(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Function __f) @@ -39,7 +39,7 @@ __pattern_walk1_async(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _For auto __n = __last - __first; assert(__n > 0); - auto __keep = oneapi::dpl::__ranges::__get_sycl_range<__acc_mode, _IsNoInitRequested>(); + auto __keep = oneapi::dpl::__ranges::__get_sycl_range<__acc_mode, _IsNoInitRequested, _DeferToUserHint>(); auto __buf = __keep(__first, __last); auto __future_obj = oneapi::dpl::__par_backend_hetero::__parallel_for( @@ -108,6 +108,16 @@ __pattern_walk2_brick_async(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __first1, __last1, __first2, __brick); } +template +auto +__pattern_for_each_async(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ForwardIterator __first, + _ForwardIterator __last, _Function __f) +{ + return __pattern_walk1_async<__par_backend_hetero::access_mode::read_write, /*_IsNoInitRequested=*/false, + /*_DeferToUserHint=*/true>( + __hetero_tag<_BackendTag>{}, std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); +} + //------------------------------------------------------------------------ // transform_reduce (version with two binary functions) //------------------------------------------------------------------------ @@ -169,9 +179,7 @@ __pattern_fill_async(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __exec, _ForwardIterator __last, const _T& __value) { return __pattern_walk1_async<__par_backend_hetero::access_mode::write, /*_IsNoInitRequested=*/true>( - __tag, ::std::forward<_ExecutionPolicy>(__exec), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__last), + __tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, oneapi::dpl::__internal::__brick_fill<__hetero_tag<_BackendTag>, _T>{__value}); } diff --git a/include/oneapi/dpl/internal/async_impl/glue_async_impl.h b/include/oneapi/dpl/internal/async_impl/glue_async_impl.h index 5acb764abf3..b120f5e35b5 100644 --- a/include/oneapi/dpl/internal/async_impl/glue_async_impl.h +++ b/include/oneapi/dpl/internal/async_impl/glue_async_impl.h @@ -130,9 +130,8 @@ for_each_async(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIter const auto __dispatch_tag = oneapi::dpl::__internal::__select_backend(__exec, __first); wait_for_all(::std::forward<_Events>(__dependencies)...); - auto ret_val = oneapi::dpl::__internal::__pattern_walk1_async<__par_backend_hetero::access_mode::read_write, - /*_IsNoInitRequested=*/false>( - __dispatch_tag, ::std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); + auto ret_val = oneapi::dpl::__internal::__pattern_for_each_async( + __dispatch_tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); return ret_val; } diff --git a/include/oneapi/dpl/pstl/algorithm_fwd.h b/include/oneapi/dpl/pstl/algorithm_fwd.h index 0de06e55d9d..f23482ad57d 100644 --- a/include/oneapi/dpl/pstl/algorithm_fwd.h +++ b/include/oneapi/dpl/pstl/algorithm_fwd.h @@ -74,6 +74,10 @@ template , _ExecutionPolicy&&, _RandomAccessIterator, _RandomAccessIterator, _Function); +template +void +__pattern_for_each(_Tag, _ExecutionPolicy&&, _ForwardIterator, _ForwardIterator, _Function); + //------------------------------------------------------------------------ // walk1_n //------------------------------------------------------------------------ @@ -94,6 +98,10 @@ template , _ExecutionPolicy&&, _RandomAccessIterator, _Size, _Function); +template +_ForwardIterator +__pattern_for_each_n(_Tag, _ExecutionPolicy&&, _ForwardIterator, _Size, _Function); + //------------------------------------------------------------------------ // walk2 (pseudo) // diff --git a/include/oneapi/dpl/pstl/algorithm_impl.h b/include/oneapi/dpl/pstl/algorithm_impl.h index 7cc71a9d8b1..290b0a7ee9f 100644 --- a/include/oneapi/dpl/pstl/algorithm_impl.h +++ b/include/oneapi/dpl/pstl/algorithm_impl.h @@ -178,6 +178,13 @@ __pattern_walk1(__parallel_tag<_IsVector>, _ExecutionPolicy&& __exec, _RandomAcc }); } +template +void +__pattern_for_each(_Tag, _ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Function __f) +{ + __pattern_walk1(_Tag{}, std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); +} + //------------------------------------------------------------------------ // walk1_n //------------------------------------------------------------------------ @@ -216,6 +223,13 @@ __pattern_walk1_n(__parallel_tag<_IsVector> __tag, _ExecutionPolicy&& __exec, _R return __first + __n; } +template +_ForwardIterator +__pattern_for_each_n(_Tag, _ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __n, _Function __f) +{ + return __pattern_walk1_n(_Tag{}, std::forward<_ExecutionPolicy>(__exec), __first, __n, __f); +} + //------------------------------------------------------------------------ // walk2 (pseudo) // diff --git a/include/oneapi/dpl/pstl/glue_algorithm_impl.h b/include/oneapi/dpl/pstl/glue_algorithm_impl.h index 4f480acdd0d..b1d5fc7ef52 100644 --- a/include/oneapi/dpl/pstl/glue_algorithm_impl.h +++ b/include/oneapi/dpl/pstl/glue_algorithm_impl.h @@ -78,8 +78,8 @@ for_each(_ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator _ { const auto __dispatch_tag = oneapi::dpl::__internal::__select_backend(__exec, __first); - oneapi::dpl::__internal::__pattern_walk1(__dispatch_tag, ::std::forward<_ExecutionPolicy>(__exec), __first, __last, - __f); + oneapi::dpl::__internal::__pattern_for_each(__dispatch_tag, ::std::forward<_ExecutionPolicy>(__exec), __first, + __last, __f); } template @@ -88,8 +88,8 @@ for_each_n(_ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __n, _Func { const auto __dispatch_tag = oneapi::dpl::__internal::__select_backend(__exec, __first); - return oneapi::dpl::__internal::__pattern_walk1_n(__dispatch_tag, ::std::forward<_ExecutionPolicy>(__exec), __first, - __n, __f); + return oneapi::dpl::__internal::__pattern_for_each_n(__dispatch_tag, ::std::forward<_ExecutionPolicy>(__exec), + __first, __n, __f); } // [alg.find] diff --git a/include/oneapi/dpl/pstl/hetero/algorithm_impl_hetero.h b/include/oneapi/dpl/pstl/hetero/algorithm_impl_hetero.h index 1422749848a..8667343ea0f 100644 --- a/include/oneapi/dpl/pstl/hetero/algorithm_impl_hetero.h +++ b/include/oneapi/dpl/pstl/hetero/algorithm_impl_hetero.h @@ -43,8 +43,8 @@ namespace __internal // walk1 //------------------------------------------------------------------------ -template <__par_backend_hetero::access_mode __acc_mode, bool _IsNoInitRequested, typename _BackendTag, - typename _ExecutionPolicy, typename _ForwardIterator, typename _Function> +template <__par_backend_hetero::access_mode __acc_mode, bool _IsNoInitRequested, bool _DeferToUserHint = false, + typename _BackendTag, typename _ExecutionPolicy, typename _ForwardIterator, typename _Function> void __pattern_hetero_walk1(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ForwardIterator __first, _ForwardIterator __last, _Function __f) @@ -53,7 +53,7 @@ __pattern_hetero_walk1(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _Fo if (__n <= 0) return; - auto __keep = oneapi::dpl::__ranges::__get_sycl_range<__acc_mode, _IsNoInitRequested>(); + auto __keep = oneapi::dpl::__ranges::__get_sycl_range<__acc_mode, _IsNoInitRequested, _DeferToUserHint>(); auto __buf = __keep(__first, __last); oneapi::dpl::__par_backend_hetero::__parallel_for( @@ -71,6 +71,16 @@ __pattern_walk1(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ForwardIt __hetero_tag<_BackendTag>{}, std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); } +template +void +__pattern_for_each(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ForwardIterator __first, + _ForwardIterator __last, _Function __f) +{ + __pattern_hetero_walk1<__par_backend_hetero::access_mode::read_write, /*_IsNoInitRequested=*/false, + /*_DeferToUserHint=*/true>(__hetero_tag<_BackendTag>{}, + std::forward<_ExecutionPolicy>(__exec), __first, __last, __f); +} + //------------------------------------------------------------------------ // walk1_n //------------------------------------------------------------------------ @@ -86,6 +96,18 @@ __pattern_walk1_n(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __exec, _F return __first + __n; } +template +_ForwardIterator +__pattern_for_each_n(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __exec, _ForwardIterator __first, _Size __n, + _Function __f) +{ + __pattern_hetero_walk1<__par_backend_hetero::access_mode::read_write, /*_IsNoInitRequested=*/false, + /*_DeferToUserHint=*/true>(__tag, std::forward<_ExecutionPolicy>(__exec), __first, + __first + __n, __f); + return __first + __n; +} + //------------------------------------------------------------------------ // walk2 //------------------------------------------------------------------------ @@ -302,9 +324,7 @@ __pattern_fill(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __exec, _Forw _ForwardIterator __last, const _T& __value) { __pattern_hetero_walk1<__par_backend_hetero::access_mode::write, /*_IsNoInitRequested=*/true>( - __tag, std::forward<_ExecutionPolicy>(__exec), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__last), + __tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, __brick_fill<__hetero_tag<_BackendTag>, _T>{__value}); return __last; } @@ -340,10 +360,7 @@ __pattern_generate(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __exec, _ _ForwardIterator __last, _Generator __g) { __pattern_hetero_walk1<__par_backend_hetero::access_mode::write, /*_IsNoInitRequested=*/true>( - __tag, std::forward<_ExecutionPolicy>(__exec), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__last), - generate_functor<_Generator>{__g}); + __tag, std::forward<_ExecutionPolicy>(__exec), __first, __last, generate_functor<_Generator>{__g}); return __last; } @@ -919,9 +936,7 @@ __pattern_partition_copy(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _ auto __keep1 = oneapi::dpl::__ranges::__get_sycl_range<__par_backend_hetero::access_mode::read>(); auto __buf1 = __keep1(__first, __last); - auto __zipped_res = __par_backend_hetero::zip( - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__result1), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__result2)); + auto __zipped_res = __par_backend_hetero::zip(__result1, __result2); auto __keep2 = oneapi::dpl::__ranges::__get_sycl_range<__par_backend_hetero::access_mode::write, /*_IsNoInitRequested=*/true>(); @@ -1222,12 +1237,7 @@ __pattern_inplace_merge(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& __ex auto __copy_first = __buf.get(); auto __copy_last = __copy_first + __n; - __pattern_merge( - __tag, __exec, __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read>(__first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read>(__middle), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read>(__middle), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read>(__last), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::write>(__copy_first), __comp); + __pattern_merge(__tag, __exec, __first, __middle, __middle, __last, __copy_first, __comp); //TODO: optimize copy back depending on Iterator, i.e. set_final_data for host iterator/pointer @@ -1468,11 +1478,8 @@ __pattern_partial_sort(__hetero_tag<_BackendTag>, _ExecutionPolicy&& __exec, _It if (__last - __first < 2) return; - __par_backend_hetero::__parallel_partial_sort( - _BackendTag{}, ::std::forward<_ExecutionPolicy>(__exec), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__mid), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__last), __comp) + __par_backend_hetero::__parallel_partial_sort(_BackendTag{}, std::forward<_ExecutionPolicy>(__exec), __first, __mid, + __last, __comp) .__checked_deferrable_wait(); } @@ -1569,10 +1576,8 @@ __pattern_partial_sort_copy(__hetero_tag<_BackendTag> __tag, _ExecutionPolicy&& // the patterns: __pattern_hetero_walk2, __parallel_partial_sort and __pattern_hetero_walk2. __par_backend_hetero::__parallel_partial_sort( - _BackendTag{}, __par_backend_hetero::make_wrapped_policy<__partial_sort_2>(__exec), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__buf_first), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__buf_mid), - __par_backend_hetero::make_iter_mode<__par_backend_hetero::access_mode::read_write>(__buf_last), __comp); + _BackendTag{}, __par_backend_hetero::make_wrapped_policy<__partial_sort_2>(__exec), __buf_first, __buf_mid, + __buf_last, __comp); return __pattern_hetero_walk2<__par_backend_hetero::__deferrable_mode, __par_backend_hetero::access_mode::write, /*_IsOutNoInitRequested=*/true>( diff --git a/include/oneapi/dpl/pstl/hetero/dpcpp/parallel_backend_sycl.h b/include/oneapi/dpl/pstl/hetero/dpcpp/parallel_backend_sycl.h index f1da2184988..aca43ba4211 100644 --- a/include/oneapi/dpl/pstl/hetero/dpcpp/parallel_backend_sycl.h +++ b/include/oneapi/dpl/pstl/hetero/dpcpp/parallel_backend_sycl.h @@ -66,136 +66,6 @@ namespace dpl namespace __par_backend_hetero { -//----------------------------------------------------------------------------- -//- iter_mode_resolver -//----------------------------------------------------------------------------- - -// iter_mode_resolver resolves the situations when -// the access mode provided by a user differs (inMode) from -// the access mode required by an algorithm (outMode). -// In general case iter_mode_resolver accepts the only situations -// when inMode == outMode, -// whereas the template specializations describe cases with specific -// inMode and outMode and the preferred access mode between the two. -template -struct iter_mode_resolver -{ - static_assert(inMode == outMode, "Access mode provided by user conflicts with the one required by the algorithm"); - static constexpr access_mode value = inMode; -}; - -template <> -struct iter_mode_resolver -{ - static constexpr access_mode value = access_mode::read; -}; - -template <> -struct iter_mode_resolver -{ - static constexpr access_mode value = access_mode::write; -}; - -template <> -struct iter_mode_resolver -{ - //TODO: warn user that the access mode is changed - static constexpr access_mode value = access_mode::read; -}; - -template <> -struct iter_mode_resolver -{ - //TODO: warn user that the access mode is changed - static constexpr access_mode value = access_mode::write; -}; - -template <> -struct iter_mode_resolver -{ - static constexpr access_mode value = access_mode::discard_write; -}; - -template <> -struct iter_mode_resolver -{ - //TODO: warn user that the access mode is changed - static constexpr access_mode value = access_mode::write; -}; - -template <> -struct iter_mode_resolver -{ - static constexpr access_mode value = access_mode::discard_read_write; -}; - -//----------------------------------------------------------------------------- -//- iter_mode -//----------------------------------------------------------------------------- - -// create iterator with different access mode -template -struct iter_mode -{ - // for common heterogeneous iterator - template