Cabana 0.8.0-dev
 
Loading...
Searching...
No Matches
Cabana_Slice.hpp
Go to the documentation of this file.
1/****************************************************************************
2 * Copyright (c) 2018-2023 by the Cabana authors *
3 * All rights reserved. *
4 * *
5 * This file is part of the Cabana library. Cabana is distributed under a *
6 * BSD 3-clause license. For the licensing terms see the LICENSE file in *
7 * the top-level directory. *
8 * *
9 * SPDX-License-Identifier: BSD-3-Clause *
10 ****************************************************************************/
11
16#ifndef CABANA_SLICE_HPP
17#define CABANA_SLICE_HPP
18
19#include <Cabana_Types.hpp>
20#include <Cabana_Utils.hpp>
21#include <impl/Cabana_Index.hpp>
22#include <impl/Cabana_TypeTraits.hpp>
23
24#include <Kokkos_Core.hpp>
25
26#include <cstdlib>
27#include <string>
28#include <type_traits>
29
30//---------------------------------------------------------------------------//
31namespace Kokkos
32{
33//---------------------------------------------------------------------------//
35template <int SOASTRIDE, int VLEN, int DIM0 = 0, int DIM1 = 0, int DIM2 = 0,
36 int DIM3 = 0, int DIM4 = 0, int DIM5 = 0>
38{
42 enum
43 {
44 is_extent_constructible = true
45 };
46
48 static constexpr int Stride = SOASTRIDE;
50 static constexpr int VectorLength = VLEN;
52 static constexpr int D0 = DIM0;
54 static constexpr int D1 = DIM1;
56 static constexpr int D2 = DIM2;
58 static constexpr int D3 = DIM3;
60 static constexpr int D4 = DIM4;
62 static constexpr int D5 = DIM5;
63
65 size_t dimension[ARRAY_LAYOUT_MAX_RANK];
66
75
77 KOKKOS_INLINE_FUNCTION
78 explicit constexpr LayoutCabanaSlice( size_t num_soa = 0,
79 size_t vector_length = VectorLength,
80 size_t d0 = D0, size_t d1 = D1,
81 size_t d2 = D2, size_t d3 = D3,
82 size_t d4 = D4, size_t d5 = D5 )
83 : dimension{ num_soa, vector_length, d0, d1, d2, d3, d4, d5 }
84 {
85 }
86};
87
88//---------------------------------------------------------------------------//
89namespace Impl
90{
92
93//---------------------------------------------------------------------------//
94// View offset of LayoutCabanaSlice.
95template <class Dimension, int... LayoutDims>
96struct ViewOffset<Dimension, Kokkos::LayoutCabanaSlice<LayoutDims...>, void>
97{
98 public:
99 using is_mapping_plugin = std::true_type;
100 using is_regular = std::true_type;
101
102 typedef size_t size_type;
103 typedef Dimension dimension_type;
104 typedef Kokkos::LayoutCabanaSlice<LayoutDims...> array_layout;
105
106 static constexpr int Stride = array_layout::Stride;
107 static constexpr int VectorLength = array_layout::VectorLength;
108 static constexpr int D0 = array_layout::D0;
109 static constexpr int D1 = array_layout::D1;
110 static constexpr int D2 = array_layout::D2;
111 static constexpr int D3 = array_layout::D3;
112 static constexpr int D4 = array_layout::D4;
113 static constexpr int D5 = array_layout::D5;
114
115 dimension_type m_dim;
116
117 //----------------------------------------
118
119 // rank 1
120 template <typename S>
121 KOKKOS_INLINE_FUNCTION constexpr size_type operator()( S const& s ) const
122 {
123 return Stride * s;
124 }
125
126 // rank 2
127 template <typename S, typename A>
128 KOKKOS_INLINE_FUNCTION constexpr size_type operator()( S const& s,
129 A const& a ) const
130 {
131 return Stride * s + a;
132 }
133
134 // rank 3
135 template <typename S, typename A, typename I0>
136 KOKKOS_INLINE_FUNCTION constexpr size_type
137 operator()( S const& s, A const& a, I0 const& i0 ) const
138 {
139 return Stride * s + a + VectorLength * i0;
140 }
141
142 // rank 4
143 template <typename S, typename A, typename I0, typename I1>
144 KOKKOS_INLINE_FUNCTION constexpr size_type
145 operator()( S const& s, A const& a, I0 const& i0, I1 const& i1 ) const
146 {
147 return Stride * s + a + VectorLength * ( i1 + D1 * i0 );
148 }
149
150 // rank 5
151 template <typename S, typename A, typename I0, typename I1, typename I2>
152 KOKKOS_INLINE_FUNCTION constexpr size_type
153 operator()( S const& s, A const& a, I0 const& i0, I1 const& i1,
154 I2 const& i2 ) const
155 {
156 return Stride * s + a + VectorLength * ( i2 + D2 * ( i1 + D1 * i0 ) );
157 }
158
159 // rank 6
160 template <typename S, typename A, typename I0, typename I1, typename I2,
161 typename I3>
162 KOKKOS_INLINE_FUNCTION constexpr size_type
163 operator()( S const& s, A const& a, I0 const& i0, I1 const& i1,
164 I2 const& i2, I3 const& i3 ) const
165 {
166 return Stride * s + a +
167 VectorLength * ( i3 + D3 * i2 + D2 * ( i1 + D1 * i0 ) );
168 }
169
170 // rank 7
171 template <typename S, typename A, typename I0, typename I1, typename I2,
172 typename I3, typename I4>
173 KOKKOS_INLINE_FUNCTION constexpr size_type
174 operator()( S const& s, A const& a, I0 const& i0, I1 const& i1,
175 I2 const& i2, I3 const& i3, I4 const& i4 ) const
176 {
177 return Stride * s + a +
178 VectorLength *
179 ( i4 + D4 * ( i3 + D3 * i2 + D2 * ( i1 + D1 * i0 ) ) );
180 }
181
182 // rank 8
183 template <typename S, typename A, typename I0, typename I1, typename I2,
184 typename I3, typename I4, typename I5>
185 KOKKOS_INLINE_FUNCTION constexpr size_type
186 operator()( S const& s, A const& a, I0 const& i0, I1 const& i1,
187 I2 const& i2, I3 const& i3, I4 const& i4, I5 const& i5 ) const
188 {
189 return Stride * s + a +
190 VectorLength *
191 ( i5 + D5 * ( i4 + D4 * ( i3 + D3 * i2 +
192 D2 * ( i1 + D1 * i0 ) ) ) );
193 }
194
195 //----------------------------------------
196
197 KOKKOS_INLINE_FUNCTION
198 constexpr array_layout layout() const { return array_layout( m_dim.N0 ); }
199
200 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_0() const
201 {
202 return m_dim.N0;
203 }
204 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_1() const
205 {
206 return m_dim.N1;
207 }
208 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_2() const
209 {
210 return m_dim.N2;
211 }
212 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_3() const
213 {
214 return m_dim.N3;
215 }
216 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_4() const
217 {
218 return m_dim.N4;
219 }
220 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_5() const
221 {
222 return m_dim.N5;
223 }
224 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_6() const
225 {
226 return m_dim.N6;
227 }
228 KOKKOS_INLINE_FUNCTION constexpr size_type dimension_7() const
229 {
230 return m_dim.N7;
231 }
232
233 /* Cardinality of the domain index space */
234 KOKKOS_INLINE_FUNCTION
235 constexpr size_type size() const
236 {
237 return m_dim.N0 * m_dim.N1 * m_dim.N2 * m_dim.N3 * m_dim.N4 * m_dim.N5 *
238 m_dim.N6 * m_dim.N7;
239 }
240
241 /* Span of the range space, largest stride * dimension */
242 KOKKOS_INLINE_FUNCTION
243 constexpr size_type span() const { return m_dim.N0 * Stride; }
244
245 KOKKOS_INLINE_FUNCTION constexpr bool span_is_contiguous() const
246 {
247 return span() == size();
248 }
249
250 /* Strides of dimensions */
251 KOKKOS_INLINE_FUNCTION constexpr size_type stride_0() const
252 {
253 return Stride;
254 }
255
256 KOKKOS_INLINE_FUNCTION constexpr size_type stride_1() const { return 1; }
257
258 KOKKOS_INLINE_FUNCTION constexpr size_type stride_2() const
259 {
260 return m_dim.N7 * m_dim.N6 * m_dim.N5 * m_dim.N4 * m_dim.N3 *
261 VectorLength;
262 }
263
264 KOKKOS_INLINE_FUNCTION constexpr size_type stride_3() const
265 {
266 return m_dim.N7 * m_dim.N6 * m_dim.N5 * m_dim.N4 * VectorLength;
267 }
268
269 KOKKOS_INLINE_FUNCTION constexpr size_type stride_4() const
270 {
271 return m_dim.N7 * m_dim.N6 * m_dim.N5 * VectorLength;
272 }
273
274 KOKKOS_INLINE_FUNCTION constexpr size_type stride_5() const
275 {
276 return m_dim.N7 * m_dim.N6 * VectorLength;
277 }
278
279 KOKKOS_INLINE_FUNCTION constexpr size_type stride_6() const
280 {
281 return m_dim.N7 * VectorLength;
282 }
283
284 KOKKOS_INLINE_FUNCTION constexpr size_type stride_7() const
285 {
286 return VectorLength;
287 }
288
289 // Stride with [ rank ] value is the total length
290 template <typename iType>
291 KOKKOS_INLINE_FUNCTION void stride( iType* const s ) const
292 {
293 if ( 0 < dimension_type::rank )
294 {
295 s[0] = stride_0();
296 }
297 if ( 1 < dimension_type::rank )
298 {
299 s[1] = stride_1();
300 }
301 if ( 2 < dimension_type::rank )
302 {
303 s[2] = stride_2();
304 }
305 if ( 3 < dimension_type::rank )
306 {
307 s[3] = stride_3();
308 }
309 if ( 4 < dimension_type::rank )
310 {
311 s[4] = stride_4();
312 }
313 if ( 5 < dimension_type::rank )
314 {
315 s[5] = stride_5();
316 }
317 if ( 6 < dimension_type::rank )
318 {
319 s[6] = stride_6();
320 }
321 if ( 7 < dimension_type::rank )
322 {
323 s[7] = stride_7();
324 }
325 s[dimension_type::rank] = span();
326 }
327
328 //----------------------------------------
329
330 ViewOffset() = default;
331 ViewOffset( const ViewOffset& ) = default;
332 ViewOffset& operator=( const ViewOffset& ) = default;
333
334 KOKKOS_INLINE_FUNCTION
335 constexpr ViewOffset( std::integral_constant<unsigned, 0> const&,
336 Kokkos::LayoutCabanaSlice<LayoutDims...> const& rhs )
337 : m_dim( rhs.dimension[0], rhs.dimension[1], rhs.dimension[2],
338 rhs.dimension[3], rhs.dimension[4], rhs.dimension[5],
339 rhs.dimension[6], rhs.dimension[7] )
340 {
341 }
342
343 template <class DimRHS, class LayoutRHS>
344 KOKKOS_INLINE_FUNCTION constexpr ViewOffset(
345 const ViewOffset<DimRHS, LayoutRHS, void>& rhs )
346 : m_dim( rhs.m_dim.N0, rhs.m_dim.N1, rhs.m_dim.N2, rhs.m_dim.N3,
347 rhs.m_dim.N4, rhs.m_dim.N5, rhs.m_dim.N6, rhs.m_dim.N7 )
348 {
349 static_assert( int( DimRHS::rank ) == int( dimension_type::rank ),
350 "ViewOffset assignment requires equal rank" );
351 }
352
353 //----------------------------------------
354 // Subview construction
355
356 template <class DimRHS, class LayoutRHS>
357 KOKKOS_INLINE_FUNCTION constexpr ViewOffset(
358 const ViewOffset<DimRHS, LayoutRHS, void>&,
359 const SubviewExtents<DimRHS::rank, dimension_type::rank>& sub )
360 : m_dim( sub.range_extent( 0 ), sub.range_extent( 1 ),
361 sub.range_extent( 2 ), sub.range_extent( 3 ),
362 sub.range_extent( 4 ), sub.range_extent( 5 ),
363 sub.range_extent( 6 ), sub.range_extent( 7 ) )
364 {
365 }
366};
367
368//---------------------------------------------------------------------------//
369
371} // namespace Impl
372
373} // end namespace Kokkos
374
375//---------------------------------------------------------------------------//
376namespace Cabana
377{
378namespace Impl
379{
381
382//---------------------------------------------------------------------------//
383// Given a tuple member type T of the given rank get the Kokkos view
384// data layout parameters. The tuple index effectively introduces 2 new
385// dimensions to the problem on top of the member dimensions - one for the
386// struct index and one for the vector index.
387template <typename T, std::size_t Rank, int VectorLength, int Stride>
388struct KokkosDataTypeImpl;
389
390// Rank-0
391template <typename T, int VectorLength, int Stride>
392struct KokkosDataTypeImpl<T, 0, VectorLength, Stride>
393{
394 using value_type = typename std::remove_all_extents<T>::type;
395 using data_type = value_type* [VectorLength];
396 using cabana_layout = Kokkos::LayoutCabanaSlice<Stride, VectorLength>;
397
398 inline static cabana_layout createLayout( const std::size_t num_soa )
399 {
400 return cabana_layout( num_soa );
401 }
402};
403
404// Rank-1
405template <typename T, int VectorLength, int Stride>
406struct KokkosDataTypeImpl<T, 1, VectorLength, Stride>
407{
408 using value_type = typename std::remove_all_extents<T>::type;
409 static constexpr std::size_t D0 = std::extent<T, 0>::value;
410 using data_type = value_type* [VectorLength][D0];
411 using cabana_layout = Kokkos::LayoutCabanaSlice<Stride, VectorLength, D0>;
412
413 inline static cabana_layout createLayout( const std::size_t num_soa )
414 {
415 return cabana_layout( num_soa );
416 }
417};
418
419// Rank-2
420template <typename T, int VectorLength, int Stride>
421struct KokkosDataTypeImpl<T, 2, VectorLength, Stride>
422{
423 using value_type = typename std::remove_all_extents<T>::type;
424 static constexpr std::size_t D0 = std::extent<T, 0>::value;
425 static constexpr std::size_t D1 = std::extent<T, 1>::value;
426 using data_type = value_type* [VectorLength][D0][D1];
427 using cabana_layout =
428 Kokkos::LayoutCabanaSlice<Stride, VectorLength, D0, D1>;
429
430 inline static cabana_layout createLayout( const std::size_t num_soa )
431 {
432 return cabana_layout( num_soa );
433 }
434};
435
436// Rank-3
437template <typename T, int VectorLength, int Stride>
438struct KokkosDataTypeImpl<T, 3, VectorLength, Stride>
439{
440 using value_type = typename std::remove_all_extents<T>::type;
441 static constexpr std::size_t D0 = std::extent<T, 0>::value;
442 static constexpr std::size_t D1 = std::extent<T, 1>::value;
443 static constexpr std::size_t D2 = std::extent<T, 2>::value;
444 using data_type = value_type* [VectorLength][D0][D1][D2];
445 using cabana_layout =
446 Kokkos::LayoutCabanaSlice<Stride, VectorLength, D0, D1, D2>;
447
448 inline static cabana_layout createLayout( const std::size_t num_soa )
449 {
450 return cabana_layout( num_soa );
451 }
452};
453
454// Data type specialization.
455template <typename T, int VectorLength, int Stride>
456struct KokkosDataType
457{
458 using kokkos_data_type =
459 KokkosDataTypeImpl<T, std::rank<T>::value, VectorLength, Stride>;
460 using data_type = typename kokkos_data_type::data_type;
461 using cabana_layout = typename kokkos_data_type::cabana_layout;
462
463 inline static cabana_layout createLayout( const std::size_t num_soa )
464 {
465 return kokkos_data_type::createLayout( num_soa );
466 }
467};
468
469//---------------------------------------------------------------------------//
470// Kokkos view wrapper for tuple members
471template <typename T, int VectorLength, int Stride,
472 typename std::enable_if<
473 Impl::IsVectorLengthValid<VectorLength>::value, int>::type = 0>
474struct KokkosViewWrapper
475{
476 using data_type =
477 typename KokkosDataType<T, VectorLength, Stride>::data_type;
478
479 using cabana_layout =
480 typename KokkosDataType<T, VectorLength, Stride>::cabana_layout;
481
482 inline static cabana_layout createLayout( const std::size_t num_soa )
483 {
484 return KokkosDataType<T, VectorLength, Stride>::createLayout( num_soa );
485 }
486};
487
488//---------------------------------------------------------------------------//
489
491} // end namespace Impl
492
493//---------------------------------------------------------------------------//
498//---------------------------------------------------------------------------//
499template <typename DataType, typename MemorySpace, typename MemoryAccessType,
500 int VectorLength, int Stride>
501class Slice
502{
503 public:
504 // Ensure the vector length is valid.
505 static_assert( Impl::IsVectorLengthValid<VectorLength>::value,
506 "Vector length must be valid" );
507
511
512 // FIXME: extracting the self type for backwards compatibility with previous
513 // template on DeviceType. Should simply be MemorySpace after next release.
515 using memory_space = typename MemorySpace::memory_space;
516 // FIXME: replace warning with memory space assert after next release.
517 static_assert( Impl::deprecated( Kokkos::is_device<MemorySpace>() ) );
518
520 using device_type [[deprecated]] = typename memory_space::device_type;
522 using execution_space = typename memory_space::execution_space;
523
525 "Slice memory access type must be a Cabana access type" );
527 using memory_access_type = MemoryAccessType;
528
530 static constexpr int vector_length = VectorLength;
531
533 static constexpr int soa_stride = Stride;
534
536 using size_type = typename memory_space::size_type;
537
540
542 static constexpr std::size_t max_supported_rank = 3;
543
545 static constexpr std::size_t max_label_length = 128;
546
549 Impl::KokkosViewWrapper<DataType, vector_length, soa_stride>;
550
553 Kokkos::View<typename view_wrapper::data_type,
554 typename view_wrapper::cabana_layout, MemorySpace,
555 typename MemoryAccessType::kokkos_memory_traits>;
556
558 using reference_type = typename kokkos_view::reference_type;
560 using value_type = typename kokkos_view::value_type;
562 using pointer_type = typename kokkos_view::pointer_type;
564 using view_layout = typename kokkos_view::array_layout;
565
575
576 // Declare slices of different memory access types to be friends.
577 friend class Slice<DataType, MemorySpace, DefaultAccessMemory, VectorLength,
578 Stride>;
579 friend class Slice<DataType, MemorySpace, AtomicAccessMemory, VectorLength,
580 Stride>;
581 friend class Slice<DataType, MemorySpace, RandomAccessMemory, VectorLength,
582 Stride>;
583
584 // Equivalent Kokkos view rank. This rank assumes that the struct and
585 // array dimension are merged. For the true rank of the raw AoSoA data use
586 // the rank() function below which will account for the extra dimension
587 // from separate struct and array indices. This enumeration is for
588 // compatibility with Kokkos views.
589 enum
590 {
591 rank = std::rank<DataType>::value + 1
592 };
593
594 public:
599 : _size( 0 )
600 {
601 }
602
611 const size_type num_soa, const std::string& label = "" )
612 : _view( data, view_wrapper::createLayout( num_soa ) )
613 , _size( size )
614 {
615 std::strcpy( _label, label.c_str() );
616 }
617
625 template <class MAT>
627 : _view( rhs._view )
628 , _size( rhs._size )
629 {
630 std::strcpy( _label, rhs._label );
631 }
632
642 template <class MAT>
645 {
646 _view = rhs._view;
647 _size = rhs._size;
648 std::strcpy( _label, rhs._label );
649 return *this;
650 }
651
657 std::string label() const { return std::string( _label ); }
658
663 KOKKOS_INLINE_FUNCTION
664 size_type size() const { return _size; }
665
670 KOKKOS_INLINE_FUNCTION
671 size_type numSoA() const { return _view.extent( 0 ); }
672
678 KOKKOS_INLINE_FUNCTION
680 {
681 return ( static_cast<size_type>( s ) < _view.extent( 0 ) - 1 )
683 : ( _size % vector_length );
684 }
685
686 // ------------
687 // 2-D accessor
688
690 template <typename U = DataType>
691 KOKKOS_FORCEINLINE_FUNCTION
692 typename std::enable_if<( 0 == std::rank<U>::value &&
693 std::is_same<U, DataType>::value ),
694 reference_type>::type
695 access( const size_type s, const size_type a ) const
696 {
697 return _view( s, a );
698 }
699
701 template <typename U = DataType>
702 KOKKOS_FORCEINLINE_FUNCTION
703 typename std::enable_if<( 1 == std::rank<U>::value &&
704 std::is_same<U, DataType>::value ),
705 reference_type>::type
706 access( const size_type s, const size_type a, const size_type d0 ) const
707 {
708 return _view( s, a, d0 );
709 }
710
712 template <typename U = DataType>
713 KOKKOS_FORCEINLINE_FUNCTION
714 typename std::enable_if<( 2 == std::rank<U>::value &&
715 std::is_same<U, DataType>::value ),
716 reference_type>::type
717 access( const size_type s, const size_type a, const size_type d0,
718 const size_type d1 ) const
719 {
720 return _view( s, a, d0, d1 );
721 }
722
724 template <typename U = DataType>
725 KOKKOS_FORCEINLINE_FUNCTION
726 typename std::enable_if<( 3 == std::rank<U>::value &&
727 std::is_same<U, DataType>::value ),
728 reference_type>::type
729 access( const size_type s, const size_type a, const size_type d0,
730 const size_type d1, const size_type d2 ) const
731 {
732 return _view( s, a, d0, d1, d2 );
733 }
734
735 // ------------
736 // 1-D accessor
737
739 template <typename U = DataType>
740 KOKKOS_FORCEINLINE_FUNCTION
741 typename std::enable_if<( 0 == std::rank<U>::value &&
742 std::is_same<U, DataType>::value ),
743 reference_type>::type
744 operator()( const size_type i ) const
745 {
746 return access( index_type::s( i ), index_type::a( i ) );
747 }
748
750 template <typename U = DataType>
751 KOKKOS_FORCEINLINE_FUNCTION
752 typename std::enable_if<( 1 == std::rank<U>::value &&
753 std::is_same<U, DataType>::value ),
754 reference_type>::type
755 operator()( const size_type i, const size_type d0 ) const
756 {
757 return access( index_type::s( i ), index_type::a( i ), d0 );
758 }
759
761 template <typename U = DataType>
762 KOKKOS_FORCEINLINE_FUNCTION
763 typename std::enable_if<( 2 == std::rank<U>::value &&
764 std::is_same<U, DataType>::value ),
765 reference_type>::type
766 operator()( const size_type i, const size_type d0,
767 const size_type d1 ) const
768 {
769 return access( index_type::s( i ), index_type::a( i ), d0, d1 );
770 }
771
773 template <typename U = DataType>
774 KOKKOS_FORCEINLINE_FUNCTION
775 typename std::enable_if<( 3 == std::rank<U>::value &&
776 std::is_same<U, DataType>::value ),
777 reference_type>::type
778 operator()( const size_type i, const size_type d0, const size_type d1,
779 const size_type d2 ) const
780 {
781 return access( index_type::s( i ), index_type::a( i ), d0, d1, d2 );
782 }
783
784 // -------------------------------
785 // Raw data access.
786
791 KOKKOS_INLINE_FUNCTION
792 pointer_type data() const { return _view.data(); }
793
800 KOKKOS_INLINE_FUNCTION
801 constexpr size_type viewRank() const { return _view.rank; }
802
810 KOKKOS_INLINE_FUNCTION
811 size_type extent( const size_type d ) const { return _view.extent( d ); }
812
819 KOKKOS_INLINE_FUNCTION
820 size_type stride( const size_type d ) const { return _view.stride( d ); }
821
825 KOKKOS_INLINE_FUNCTION
826 kokkos_view view() const { return _view; }
827
828 private:
829 // The data view. This view is unmanaged and has access traits specified
830 // by the template parameters of this class.
831 kokkos_view _view;
832
833 // Number of tuples in the slice.
834 size_type _size;
835
836 // Slice label.
837 char _label[max_label_length];
838};
839
840//---------------------------------------------------------------------------//
842template <typename>
843struct is_slice_impl : public std::false_type
844{
845};
846
847// True only if the type is a member slice *AND* the member slice is templated
848// on an AoSoA type.
849template <typename DataType, typename MemorySpace, typename MemoryAccessType,
850 int VectorLength, int Stride>
851struct is_slice_impl<
852 Slice<DataType, MemorySpace, MemoryAccessType, VectorLength, Stride>>
853 : public std::true_type
854{
855};
857
859template <class T>
860struct is_slice : public is_slice_impl<typename std::remove_cv<T>::type>::type
861{
862};
863
864//---------------------------------------------------------------------------//
865// Copy to View.
866//---------------------------------------------------------------------------//
867
869template <class ExecutionSpace, class ViewType, class SliceType>
871 ExecutionSpace exec_space, ViewType& view, const SliceType& slice,
872 const std::size_t begin, const std::size_t end,
873 typename std::enable_if<
874 2 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
875{
876 Kokkos::parallel_for(
877 "Cabana::copySliceToView::Rank0",
878 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
879 KOKKOS_LAMBDA( const int i ) { view( i - begin ) = slice( i ); } );
880}
881
883template <class ExecutionSpace, class ViewType, class SliceType>
885 ExecutionSpace exec_space, ViewType& view, const SliceType& slice,
886 const std::size_t begin, const std::size_t end,
887 typename std::enable_if<
888 3 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
889{
890 Kokkos::parallel_for(
891 "Cabana::copySliceToView::FieldRank1",
892 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
893 KOKKOS_LAMBDA( const int i ) {
894 for ( std::size_t d0 = 0; d0 < slice.extent( 2 ); ++d0 )
895 view( i - begin, d0 ) = slice( i, d0 );
896 } );
897}
898
900template <class ExecutionSpace, class ViewType, class SliceType>
902 ExecutionSpace exec_space, ViewType& view, const SliceType& slice,
903 const std::size_t begin, const std::size_t end,
904 typename std::enable_if<
905 4 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
906{
907 Kokkos::parallel_for(
908 "Cabana::copySliceToView::writeFieldRank2",
909 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
910 KOKKOS_LAMBDA( const int i ) {
911 for ( std::size_t d0 = 0; d0 < slice.extent( 2 ); ++d0 )
912 for ( std::size_t d1 = 0; d1 < slice.extent( 3 ); ++d1 )
913 view( i - begin, d0, d1 ) = slice( i, d0, d1 );
914 } );
915}
916
918template <class ViewType, class SliceType>
919void copySliceToView( ViewType& view, const SliceType& slice,
920 const std::size_t begin, const std::size_t end )
921{
922 using exec_space = typename SliceType::execution_space;
923 copySliceToView( exec_space{}, view, slice, begin, end );
924}
925
926//---------------------------------------------------------------------------//
927// Copy from View.
928//---------------------------------------------------------------------------//
929
931template <class ExecutionSpace, class SliceType, class ViewType>
933 ExecutionSpace exec_space, SliceType& slice, const ViewType& view,
934 const std::size_t begin, const std::size_t end,
935 typename std::enable_if<
936 2 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
937{
938 Kokkos::parallel_for(
939 "Cabana::copyViewToSlice::Rank0",
940 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
941 KOKKOS_LAMBDA( const int i ) { slice( i - begin ) = view( i ); } );
942}
943
945template <class ExecutionSpace, class SliceType, class ViewType>
947 ExecutionSpace exec_space, SliceType& slice, const ViewType& view,
948 const std::size_t begin, const std::size_t end,
949 typename std::enable_if<
950 3 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
951{
952 Kokkos::parallel_for(
953 "Cabana::copySliceToView::FieldRank1",
954 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
955 KOKKOS_LAMBDA( const int i ) {
956 for ( std::size_t d0 = 0; d0 < slice.extent( 2 ); ++d0 )
957 slice( i - begin, d0 ) = view( i, d0 );
958 } );
959}
960
962template <class ExecutionSpace, class SliceType, class ViewType>
964 ExecutionSpace exec_space, SliceType& slice, const ViewType& view,
965 const std::size_t begin, const std::size_t end,
966 typename std::enable_if<
967 4 == SliceType::kokkos_view::traits::dimension::rank, int*>::type = 0 )
968{
969 Kokkos::parallel_for(
970 "Cabana::copySliceToView::writeFieldRank2",
971 Kokkos::RangePolicy<ExecutionSpace>( exec_space, begin, end ),
972 KOKKOS_LAMBDA( const int i ) {
973 for ( std::size_t d0 = 0; d0 < slice.extent( 2 ); ++d0 )
974 for ( std::size_t d1 = 0; d1 < slice.extent( 3 ); ++d1 )
975 slice( i - begin, d0, d1 ) = view( i, d0, d1 );
976 } );
977}
978
980template <class ViewType, class SliceType>
981void copyViewToSlice( SliceType& slice, const ViewType& view,
982 const std::size_t begin, const std::size_t end )
983{
984 using exec_space = typename SliceType::execution_space;
985 copyViewToSlice( exec_space{}, slice, view, begin, end );
986}
987
989template <class SliceType>
991 [[maybe_unused]] SliceType slice, [[maybe_unused]] const std::size_t size,
992 typename std::enable_if<is_slice<SliceType>::value, int>::type* = 0 )
993{
994 // Allow unused for release builds.
995 assert( slice.size() == size );
996}
997
999template <class ViewType>
1001 [[maybe_unused]] ViewType view, [[maybe_unused]] const std::size_t size,
1002 typename std::enable_if<Kokkos::is_view<ViewType>::value, int>::type* = 0 )
1003{
1004 // Allow unused for release builds.
1005 assert( view.extent( 0 ) == size );
1006}
1007
1008//---------------------------------------------------------------------------//
1009
1011template <class SliceType>
1012auto size( SliceType slice,
1013 typename std::enable_if<is_slice<SliceType>::value, int>::type* = 0 )
1014{
1015 return slice.size();
1016}
1017
1019template <class ViewType>
1020auto size(
1021 ViewType view,
1022 typename std::enable_if<Kokkos::is_view<ViewType>::value, int>::type* = 0 )
1023{
1024 return view.extent( 0 );
1025}
1026
1027} // end namespace Cabana
1028
1029//---------------------------------------------------------------------------//
1030
1031#endif // end CABANA_SLICE_HPP
AoSoA indexing.
Memory access type checking.
Cabana utilities.
Class for converting between 1d and 2d aosoa indices.
Definition Cabana_Index.hpp:38
static KOKKOS_FORCEINLINE_FUNCTION constexpr std::size_t a(const std::size_t i)
Definition Cabana_Index.hpp:77
static KOKKOS_FORCEINLINE_FUNCTION constexpr std::size_t s(const std::size_t i)
Definition Cabana_Index.hpp:62
A slice of an array-of-structs-of-arrays with data access to a single multidimensional member.
Definition Cabana_Slice.hpp:502
KOKKOS_FORCEINLINE_FUNCTION std::enable_if<(3==std::rank< U >::value &&std::is_same< U, DataType >::value), reference_type >::type access(const size_type s, const size_type a, const size_type d0, const size_type d1, const size_type d2) const
2d access for Rank 3
Definition Cabana_Slice.hpp:729
Slice & operator=(const Slice< DataType, MemorySpace, MAT, VectorLength, Stride > &rhs)
Assignment operator for different memory spaces for assigning new memory access traits to the view.
Definition Cabana_Slice.hpp:643
Slice< member_data_type< M >, memory_space, RandomAccessMemory, VectorLength, Stride > random_access_slice
Definition Cabana_Slice.hpp:573
KOKKOS_FORCEINLINE_FUNCTION std::enable_if<(0==std::rank< U >::value &&std::is_same< U, DataType >::value), reference_type >::type access(const size_type s, const size_type a) const
2d access for Rank 0
Definition Cabana_Slice.hpp:695
KOKKOS_INLINE_FUNCTION size_type stride(const size_type d) const
Get the stride of a given raw slice dimension. This includes the struct dimension,...
Definition Cabana_Slice.hpp:820
Slice(const pointer_type data, const size_type size, const size_type num_soa, const std::string &label="")
Constructor.
Definition Cabana_Slice.hpp:610
KOKKOS_INLINE_FUNCTION size_type arraySize(const size_type s) const
Get the size of the data array at a given struct member index.
Definition Cabana_Slice.hpp:679
KOKKOS_INLINE_FUNCTION constexpr size_type viewRank() const
Get the rank of the raw data for this slice. This includes the struct dimension, array dimension,...
Definition Cabana_Slice.hpp:801
KOKKOS_FORCEINLINE_FUNCTION std::enable_if<(1==std::rank< U >::value &&std::is_same< U, DataType >::value), reference_type >::type access(const size_type s, const size_type a, const size_type d0) const
2d access for Rank 1
Definition Cabana_Slice.hpp:706
Slice< member_data_type< M >, memory_space, DefaultAccessMemory, VectorLength, Stride > default_access_slice
Definition Cabana_Slice.hpp:567
Slice< member_data_type< M >, memory_space, AtomicAccessMemory, VectorLength, Stride > atomic_access_slice
Definition Cabana_Slice.hpp:570
Slice()
Default constructor.
Definition Cabana_Slice.hpp:598
Slice(const Slice< DataType, MemorySpace, MAT, VectorLength, Stride > &rhs)
Shallow copy constructor for different memory spaces for assigning new memory access traits to the vi...
Definition Cabana_Slice.hpp:626
KOKKOS_FORCEINLINE_FUNCTION std::enable_if<(2==std::rank< U >::value &&std::is_same< U, DataType >::value), reference_type >::type access(const size_type s, const size_type a, const size_type d0, const size_type d1) const
2d access for Rank 2
Definition Cabana_Slice.hpp:717
KOKKOS_INLINE_FUNCTION size_type extent(const size_type d) const
Get the extent of a given raw slice data dimension. This includes the struct dimension,...
Definition Cabana_Slice.hpp:811
KOKKOS_INLINE_FUNCTION kokkos_view view() const
Get the underlying Kokkos View managing the slice data.
Definition Cabana_Slice.hpp:826
KOKKOS_INLINE_FUNCTION size_type numSoA() const
Get the number of structs-of-arrays in the container.
Definition Cabana_Slice.hpp:671
Slice< member_data_type< M >, memory_space, DefaultAccessMemory, VectorLength, Stride > slice_type
Definition Cabana_Slice.hpp:509
Kokkos::View< typename view_wrapper::data_type, typename view_wrapper::cabana_layout, memory_space, typename DefaultAccessMemory::kokkos_memory_traits > kokkos_view
Definition Cabana_Slice.hpp:552
Impl::KokkosViewWrapper< member_data_type< M >, vector_length, soa_stride > view_wrapper
Definition Cabana_Slice.hpp:548
Core: particle data structures and algorithms.
Definition Cabana_AoSoA.hpp:36
auto size(SliceType slice, typename std::enable_if< is_slice< SliceType >::value, int >::type *=0)
Check slice size (differs from Kokkos View).
Definition Cabana_Slice.hpp:1012
void copyViewToSlice(ExecutionSpace exec_space, SliceType &slice, const ViewType &view, const std::size_t begin, const std::size_t end, typename std::enable_if< 2==SliceType::kokkos_view::traits::dimension::rank, int * >::type=0)
Copy from View to slice. Rank-0.
Definition Cabana_Slice.hpp:932
void copySliceToView(ExecutionSpace exec_space, ViewType &view, const SliceType &slice, const std::size_t begin, const std::size_t end, typename std::enable_if< 2==SliceType::kokkos_view::traits::dimension::rank, int * >::type=0)
Copy from slice to View. Rank-0.
Definition Cabana_Slice.hpp:870
AoSoA_t::template member_slice_type< M > slice(const AoSoA_t &aosoa, const std::string &slice_label="")
Create a slice from an AoSoA.
Definition Cabana_AoSoA.hpp:77
void checkSize(SliceType slice, const std::size_t size, typename std::enable_if< is_slice< SliceType >::value, int >::type *=0)
Check slice size (differs from Kokkos View).
Definition Cabana_Slice.hpp:990
Atomic memory access. All reads and writes are atomic.
Definition Cabana_Types.hpp:70
Definition Cabana_Types.hpp:37
Random access memory. Read-only and const with limited spatial locality.
Definition Cabana_Types.hpp:54
Memory access type checker.
Definition Cabana_Types.hpp:31
Slice static type checker.
Definition Cabana_Slice.hpp:861
Cabana Slice layout.
Definition Cabana_Slice.hpp:38
LayoutCabanaSlice & operator=(LayoutCabanaSlice const &)=default
Const assignment operator.
static constexpr int Stride
Slice SoA stride.
Definition Cabana_Slice.hpp:48
static constexpr int D0
Slice zeroth dimension size.
Definition Cabana_Slice.hpp:52
static constexpr int D4
Slice fourth dimension size.
Definition Cabana_Slice.hpp:60
LayoutCabanaSlice array_layout
Slice array layout.
Definition Cabana_Slice.hpp:40
static constexpr int D5
Slice fifth dimension size.
Definition Cabana_Slice.hpp:62
LayoutCabanaSlice(LayoutCabanaSlice &&)=default
Copy constructor.
static constexpr int D2
Slice second dimension size.
Definition Cabana_Slice.hpp:56
size_t dimension[ARRAY_LAYOUT_MAX_RANK]
Slice dimension.
Definition Cabana_Slice.hpp:65
LayoutCabanaSlice(LayoutCabanaSlice const &)=default
Const copy constructor.
LayoutCabanaSlice & operator=(LayoutCabanaSlice &&)=default
Assignment operator.
static constexpr int VectorLength
Slice vectorlength.
Definition Cabana_Slice.hpp:50
static constexpr int D1
Slice first dimension size.
Definition Cabana_Slice.hpp:54
static constexpr int D3
Slice third dimension size.
Definition Cabana_Slice.hpp:58
KOKKOS_INLINE_FUNCTION constexpr LayoutCabanaSlice(size_t num_soa=0, size_t vector_length=VectorLength, size_t d0=D0, size_t d1=D1, size_t d2=D2, size_t d3=D3, size_t d4=D4, size_t d5=D5)
Constructor.
Definition Cabana_Slice.hpp:78