IPPL API Reference
Independent Parallel Particle Layer C++ API
Loading...
Searching...
No Matches
BareField.hpp
1//
2// Class BareField
3// A BareField consists of multple LFields and represents a field.
4//
5#ifndef IPPL_BARE_FIELD_HPP
6#define IPPL_BARE_FIELD_HPP
7
8#include "Ippl.h"
9
10#include <Kokkos_ReductionIdentity.hpp>
11#include <cstdlib>
12#include <map>
13#include <utility>
14
15#include "Communicate/DataTypes.h"
16
17#include "Utility/Inform.h"
18#include "Utility/IpplInfo.h"
19
20#include "BareField.h"
21namespace Kokkos {
22 template <typename T, unsigned Dim>
23 struct reduction_identity<ippl::Vector<T, Dim>> {
24 KOKKOS_FORCEINLINE_FUNCTION static ippl::Vector<T, Dim> sum() {
25 return ippl::Vector<T, Dim>(0);
26 }
27 KOKKOS_FORCEINLINE_FUNCTION static ippl::Vector<T, Dim> prod() {
28 return ippl::Vector<T, Dim>(1);
29 }
30 KOKKOS_FORCEINLINE_FUNCTION static ippl::Vector<T, Dim> min() {
31 return ippl::Vector<T, Dim>(Kokkos::reduction_identity<T>::min());
32 }
33 KOKKOS_FORCEINLINE_FUNCTION static ippl::Vector<T, Dim> max() {
34 return ippl::Vector<T, Dim>(Kokkos::reduction_identity<T>::max());
35 }
36 };
37} // namespace Kokkos
38
39namespace KokkosCorrection {
40 template <typename Scalar, class Space = Kokkos::HostSpace>
41 struct Max : Kokkos::Max<Scalar, Space> {
42 using Super = Kokkos::Max<Scalar, Space>;
43 using value_type = typename Super::value_type;
44 KOKKOS_INLINE_FUNCTION Max(value_type& vref)
45 : Super(vref) {}
46 KOKKOS_INLINE_FUNCTION void join(value_type& dest, const value_type& src) const {
47 using ippl::max;
48 using Kokkos::max;
49 dest = max(dest, src);
50 }
51 };
52 template <typename Scalar, class Space = Kokkos::HostSpace>
53 struct Min : Kokkos::Min<Scalar, Space> {
54 using Super = Kokkos::Min<Scalar, Space>;
55 using value_type = typename Super::value_type;
56 KOKKOS_INLINE_FUNCTION Min(value_type& vref)
57 : Super(vref) {}
58 KOKKOS_INLINE_FUNCTION void join(value_type& dest, const value_type& src) const {
59 using ippl::min;
60 using Kokkos::min;
61 dest = min(dest, src);
62 }
63 };
64 template <typename Scalar, class Space = Kokkos::HostSpace>
65 struct Sum : Kokkos::Sum<Scalar, Space> {
66 using Super = Kokkos::Sum<Scalar, Space>;
67 using value_type = typename Super::value_type;
68 KOKKOS_INLINE_FUNCTION Sum(value_type& vref)
69 : Super(vref) {}
70 KOKKOS_INLINE_FUNCTION void join(value_type& dest, const value_type& src) const {
71 dest += src;
72 }
73 };
74 template <typename Scalar, class Space = Kokkos::HostSpace>
75 struct Prod : Kokkos::Prod<Scalar, Space> {
76 using Super = Kokkos::Prod<Scalar, Space>;
77 using value_type = typename Super::value_type;
78 KOKKOS_INLINE_FUNCTION Prod(value_type& vref)
79 : Super(vref) {}
80 KOKKOS_INLINE_FUNCTION void join(value_type& dest, const value_type& src) const {
81 dest *= src;
82 }
83 };
84} // namespace KokkosCorrection
85
86namespace ippl {
87 namespace detail {
88 template <typename T, unsigned Dim, class... ViewArgs>
89 struct isExpression<BareField<T, Dim, ViewArgs...>> : std::true_type {};
90 } // namespace detail
91
92 template <typename T, unsigned Dim, class... ViewArgs>
94 : nghost_m(1)
95 , layout_m(nullptr) {}
96
97 template <typename T, unsigned Dim, class... ViewArgs>
99 BareField<T, Dim, ViewArgs...> copy(*layout_m, nghost_m);
100 Kokkos::deep_copy(copy.dview_m, dview_m);
101 return copy;
102 }
103
104 template <typename T, unsigned Dim, class... ViewArgs>
106 : nghost_m(nghost)
107 // , owned_m(0)
108 , layout_m(&l) {
109 setup();
110 }
111
112 template <typename T, unsigned Dim, class... ViewArgs>
114 if (layout_m == 0) {
115 layout_m = &l;
116 nghost_m = nghost;
117 setup();
118 }
119 }
120
121 // ML
122 template <typename T, unsigned Dim, class... ViewArgs>
123 void BareField<T, Dim, ViewArgs...>::updateLayout(Layout_t& l, int nghost) {
124 // std::cout << "Got in BareField::updateLayout()" << std::endl;
125 layout_m = &l;
126 nghost_m = nghost;
127 setup();
128 }
129
130 template <typename T, unsigned Dim, class... ViewArgs>
131 void BareField<T, Dim, ViewArgs...>::setup() {
132 owned_m = layout_m->getLocalNDIndex();
133
134 auto resize = [&]<size_t... Idx>(const std::index_sequence<Idx...>&) {
135 this->resize((owned_m[Idx].length() + 2 * nghost_m)...);
136 };
137 resize(std::make_index_sequence<Dim>{});
138 }
139
140 template <typename T, unsigned Dim, class... ViewArgs>
141 template <typename... Args>
143 Kokkos::resize(dview_m, args...);
144 }
145
146 template <typename T, unsigned Dim, class... ViewArgs>
148 if (layout_m->comm.size() > 1) {
149 halo_m.fillHalo(dview_m, layout_m);
150 }
151 if (layout_m->isAllPeriodic_m) {
152 using Op = typename detail::HaloCells<T, Dim, ViewArgs...>::assign;
153 halo_m.template applyPeriodicSerialDim<Op>(dview_m, layout_m, nghost_m);
154 }
155 }
156
157 template <typename T, unsigned Dim, class... ViewArgs>
158 void BareField<T, Dim, ViewArgs...>::accumulateHalo() {
159 if (layout_m->comm.size() > 1) {
160 halo_m.accumulateHalo(dview_m, layout_m);
161 }
162 if (layout_m->isAllPeriodic_m) {
163 using Op = typename detail::HaloCells<T, Dim, ViewArgs...>::rhs_plus_assign;
164 halo_m.template applyPeriodicSerialDim<Op>(dview_m, layout_m, nghost_m);
165 }
166 }
167
168 template <typename T, unsigned Dim, class... ViewArgs>
169 void BareField<T, Dim, ViewArgs...>::accumulateHalo_noghost(int nghost) {
170 if (layout_m->comm.size() > 1) {
171 halo_m.accumulateHalo_noghost(dview_m, layout_m, nghost);
172 }
173 }
174
175 template <typename T, unsigned Dim, class... ViewArgs>
176 BareField<T, Dim, ViewArgs...>& BareField<T, Dim, ViewArgs...>::operator=(T x) {
177 Kokkos::deep_copy(dview_m, x);
178 return *this;
179 }
180
181 template <typename T, unsigned Dim, class... ViewArgs>
182 template <typename E, size_t N>
183 BareField<T, Dim, ViewArgs...>& BareField<T, Dim, ViewArgs...>::operator=(
184 const detail::Expression<E, N>& expr) {
185 using capture_type = detail::CapturedExpression<E, N>;
186 capture_type expr_ = reinterpret_cast<const capture_type&>(expr);
187 using index_array_type = typename RangePolicy<Dim, execution_space>::index_array_type;
188 ippl::parallel_for(
189 "BareField::operator=(const Expression&)", getRangePolicy(dview_m, nghost_m),
190 KOKKOS_CLASS_LAMBDA(const index_array_type& args) {
191 apply(dview_m, args) = apply(expr_, args);
192 });
193 return *this;
195
196 template <typename T, unsigned Dim, class... ViewArgs>
197 void BareField<T, Dim, ViewArgs...>::write(std::ostream& out) const {
198 Kokkos::fence();
199 detail::write<T, Dim, ViewArgs...>(dview_m, out);
201
202 template <typename T, unsigned Dim, class... ViewArgs>
204 write(inf.getDestination());
205 }
207 template <typename T, unsigned Dim, class... ViewArgs>
208 void BareField<T, Dim, ViewArgs...>::write_as_list(std::ostream& out) const {
209 Kokkos::fence();
210 detail::write_as_list<T, Dim, ViewArgs...>(dview_m, out);
211 }
213 template <typename T, unsigned Dim, class... ViewArgs>
215 write_as_list(inf.getDestination());
216 }
217
218#define DefineReduction(fun, name, op, MPI_Op) \
219 template <typename T, unsigned Dim, class... ViewArgs> \
220 T BareField<T, Dim, ViewArgs...>::name(int nghost) const { \
221 PAssert_LE(nghost, nghost_m); \
222 T temp = Kokkos::reduction_identity<T>::name(); \
223 using index_array_type = typename RangePolicy<Dim, execution_space>::index_array_type; \
224 ippl::parallel_reduce( \
225 "fun", getRangePolicy(dview_m, nghost_m - nghost), \
226 KOKKOS_CLASS_LAMBDA(const index_array_type& args, T& valL) { \
227 T myVal = apply(dview_m, args); \
228 op; \
229 }, \
230 KokkosCorrection::fun<T>(temp)); \
231 T globaltemp = 0.0; \
232 layout_m->comm.allreduce(temp, globaltemp, 1, MPI_Op<T>()); \
233 return globaltemp; \
234 }
235
236 DefineReduction(Sum, sum, valL += myVal, std::plus)
237 DefineReduction(Max, max, using Kokkos::max; valL = max(valL, myVal), std::greater)
238 DefineReduction(Min, min, using Kokkos::min; valL = min(valL, myVal), std::less)
239 DefineReduction(Prod, prod, valL *= myVal, std::multiplies)
240
241} // namespace ippl
242#endif // IPPL_BARE_FIELD_HPP
Definition Inform.h:40
Definition BareField.h:42
void initialize(Layout_t &l, int nghost=1)
Definition BareField.hpp:113
void write(std::ostream &out=std::cout) const
Definition BareField.hpp:197
BareField deepCopy() const
Definition BareField.hpp:98
BareField()
Definition BareField.hpp:93
void resize(Args... args)
Definition BareField.hpp:142
void write_as_list(std::ostream &out=std::cout) const
Definition BareField.hpp:208
Definition FieldLayout.h:166
Definition Vector.h:23
Definition Archive.h:20
KOKKOS_INLINE_FUNCTION constexpr decltype(auto) apply(const View &view, const Coords &coords)
Definition IpplOperations.h:64
RangePolicy< View::rank, typenameView::execution_space, PolicyArgs... >::policy_type getRangePolicy(const View &view, int shift=0)
Definition ParallelDispatch.h:56
Definition BareField.hpp:41
Definition BareField.hpp:53
Definition BareField.hpp:75
Definition BareField.hpp:65
Definition IpplExpressions.h:92