IPPL (Independent Parallel Particle Layer)
IPPL
Loading...
Searching...
No Matches
RegionLayout.hpp
Go to the documentation of this file.
1//
2// Class RegionLayout
3// RegionLayout stores a partitioned set of NDRegion objects, to represent
4// the parallel layout of an encompassing NDRegion. It also contains
5// functions to find the subsets of the NDRegion partitions which intersect
6// or touch a given NDRegion. It is similar to FieldLayout, with the
7// following changes:
8// 1. It uses NDRegion instead of NDIndex, so it is templated on the position
9// data type (although it can be constructed with an NDIndex and a Mesh
10// as well);
11// 2. It does not contain any consideration for guard cells;
12// 3. It can store not only the partitioned domain, but periodic copies of
13// the partitioned domain for use by particle periodic boundary conditions
14// 4. It also keeps a list of FieldLayoutUser's, so that it can notify them
15// when the internal FieldLayout here is reparitioned or otherwise changed.
16//
17// If this is constructed with a FieldLayout, it stores a pointer to it
18// so that if we must repartition the copy of the FieldLayout that
19// is stored here, we will end up repartitioning all the registered Fields.
20//
21namespace ippl {
22 namespace detail {
23 template <typename T, unsigned Dim, class Mesh, class... Properties>
25 : dLocalRegions_m("local regions (device)", 0)
26 , hLocalRegions_m(Kokkos::create_mirror_view(dLocalRegions_m)) {
27 indexOffset_m.fill(0);
28 centerOffset_m.fill(0);
29 }
30
31 template <typename T, unsigned Dim, class Mesh, class... Properties>
37
38 template <typename T, unsigned Dim, class Mesh, class... Properties>
40 const Mesh& mesh) {
41 // set our index space offset
42 for (unsigned int d = 0; d < Dim; ++d) {
43 indexOffset_m[d] = fl.getDomain()[d].first();
44 centerOffset_m[d] = 1;
45 }
46
47 region_m = convertNDIndex(fl.getDomain(), mesh);
48
49 fillRegions(fl, mesh);
50 }
51
52 // convert a given NDIndex into an NDRegion ... if this object was
53 // constructed from a FieldLayout, this does nothing, but if we are maintaining
54 // our own internal FieldLayout, we must convert from the [0,N-1] index
55 // space to our own continuous NDRegion space.
56 // NOTE: THIS ASSUMES THAT REGION'S HAVE first() < last() !!
57 template <typename T, unsigned Dim, class Mesh, class... Properties>
58 typename RegionLayout<T, Dim, Mesh, Properties...>::NDRegion_t
60 const Mesh& mesh) const {
61 // find first and last points in NDIndex and get coordinates from mesh
62 NDIndex<Dim> firstPoint, lastPoint;
63 for (unsigned int d = 0; d < Dim; d++) {
64 int first = ni[d].first() - indexOffset_m[d];
65 int last = ni[d].last() - indexOffset_m[d] + centerOffset_m[d];
66 firstPoint[d] = Index(first, first);
67 lastPoint[d] = Index(last, last);
68 }
69
70 // convert to mesh space
71 Vector<T, Dim> firstCoord = mesh.getVertexPosition(firstPoint);
72 Vector<T, Dim> lastCoord = mesh.getVertexPosition(lastPoint);
73 NDRegion_t ndregion;
74 for (unsigned int d = 0; d < Dim; d++) {
75 ndregion[d] = PRegion<T>(firstCoord(d), lastCoord(d));
76 }
77 return ndregion;
78 }
79
80 template <typename T, unsigned Dim, class Mesh, class... Properties>
82 const Mesh& mesh) {
83 using domain_type = typename FieldLayout<Dim>::host_mirror_type;
84 const domain_type& ldomains = fl.getHostLocalDomains();
85
86 Kokkos::resize(hLocalRegions_m, ldomains.size());
87 Kokkos::resize(dLocalRegions_m, ldomains.size());
88
89 using size_type = typename domain_type::size_type;
90 for (size_type i = 0; i < ldomains.size(); ++i) {
91 hLocalRegions_m(i) = convertNDIndex(ldomains(i), mesh);
92 }
93
94 Kokkos::deep_copy(dLocalRegions_m, hLocalRegions_m);
95 }
96
97 template <typename T, unsigned Dim, class Mesh, class... Properties>
99 if (Comm->rank() > 0) {
100 return;
101 }
102
103 out << "Total region = " << region_m << "\n"
104 << "Total number of subregions = " << hLocalRegions_m.size() << "\n";
105
106 using size_type = typename host_mirror_type::size_type;
107 for (size_type i = 0; i < hLocalRegions_m.size(); ++i) {
108 out << " subregion " << i << " " << hLocalRegions_m(i) << "\n";
109 }
110 }
111
112 template <typename T, unsigned Dim, class Mesh, class... Properties>
113 const typename RegionLayout<T, Dim, Mesh, Properties...>::view_type
117
118 template <typename T, unsigned Dim, class Mesh, class... Properties>
119 const typename RegionLayout<T, Dim, Mesh, Properties...>::host_mirror_type
123
124 template <typename T, unsigned Dim, class Mesh, class... Properties>
125 std::ostream& operator<<(std::ostream& out, const RegionLayout<T, Dim, Mesh>& rl) {
126 rl.write(out);
127 return out;
128 }
129 } // namespace detail
130} // namespace ippl
constexpr unsigned Dim
constexpr KOKKOS_INLINE_FUNCTION auto first()
Definition AbsorbingBC.h:10
Definition Archive.h:20
std::unique_ptr< mpi::Communicator > Comm
Definition Ippl.h:22
std::size_t size_type
Definition IpplTypes.h:13
std::ostream & operator<<(std::ostream &, const BCondBase< Field > &)
Definition BcTypes.hpp:28
typename view_type::host_mirror_type host_mirror_type
const host_mirror_type getHostLocalDomains() const
const NDIndex< Dim > & getDomain() const
KOKKOS_INLINE_FUNCTION Vector< int, Dim > last() const
Definition NDIndex.hpp:178
KOKKOS_INLINE_FUNCTION Vector< int, Dim > first() const
Definition NDIndex.hpp:170
virtual KOKKOS_INLINE_FUNCTION vector_type getVertexPosition(const NDIndex< Dim > &ndi) const =0
NDRegion_t convertNDIndex(const NDIndex< Dim > &, const Mesh &mesh) const
view_type dLocalRegions_m
local regions (device view)
host_mirror_type hLocalRegions_m
local regions (host mirror view)
const view_type getdLocalRegions() const
void fillRegions(const FieldLayout< Dim > &, const Mesh &mesh)
void write(std::ostream &=std::cout) const
std::array< int, Dim > indexOffset_m
Offset from 'normal' Index space to 'Mesh' Index space.
std::array< bool, Dim > centerOffset_m
Offset needed between centering of Index space and Mesh points.
const host_mirror_type gethLocalRegions() const
void changeDomain(const FieldLayout< Dim > &, const Mesh &mesh)