MCPcopy Create free account
hub / github.com/BLAST-WarpX/warpx / SyncCurrent

Method SyncCurrent

Source/Parallelization/WarpXComm.cpp:1169–1344  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

1167}
1168
1169void
1170WarpX::SyncCurrent (const std::string& current_fp_string)
1171{
1172 using ablastr::fields::Direction;
1173
1174 ABLASTR_PROFILE("WarpX::SyncCurrent()");
1175
1176 bool const skip_lev0_coarse_patch = true;
1177
1178 ablastr::fields::MultiLevelVectorField const& J_fp = m_fields.get_mr_levels_alldirs(current_fp_string, finest_level);
1179
1180 // If warpx.do_current_centering = 1, center currents from nodal grid to staggered grid
1181 if (do_current_centering)
1182 {
1183 ablastr::fields::MultiLevelVectorField const& J_fp_nodal = m_fields.get_mr_levels_alldirs(FieldType::current_fp_nodal, finest_level);
1184
1185 AMREX_ALWAYS_ASSERT_WITH_MESSAGE(finest_level <= 1,
1186 "warpx.do_current_centering=1 not supported with more than one fine levels");
1187 for (int lev = 0; lev <= finest_level; lev++)
1188 {
1189 constexpr auto all_dirs = std::array{Direction{0}, Direction{1}, Direction{2}};
1190 for (const auto& dir : all_dirs){
1191 ::UpdateCurrentNodalToStag(
1192 *J_fp[lev][dir], *J_fp_nodal[lev][dir],
1193 m_current_centering_nox, m_current_centering_noy, m_current_centering_noz,
1194 device_current_centering_stencil_coeffs_x,
1195 device_current_centering_stencil_coeffs_y,
1196 device_current_centering_stencil_coeffs_z);
1197 }
1198 }
1199 }
1200
1201 // If there is a single level, we apply the filter on the fp data and
1202 // then call SumBoundary that adds data from different boxes. This needs
1203 // to be done because a particle near a box boundary may deposit current
1204 // at a given (i,j,k) that is on the edge or in the ghost region of that
1205 // box while at the same time that (i,j,k) is also in the valid region
1206 // of another box. After SumBoundary, the result is as if there is only
1207 // a single box on a single process. Also note we need to call
1208 // SumBoundary even if there is only a single process, because a process
1209 // may have multiple boxes. Furthermore, even if there is only a single
1210 // box on a single process, SumBoundary should also be called if there
1211 // are periodic boundaries. So we always call SumBoundary even if it
1212 // might be a no-op in some cases, because the function does not perform
1213 // any communication if not necessary.
1214 //
1215 // When there are multiple levels, we need to send data from fine levels
1216 // to coarse levels. In the implementation below, we loop over levels
1217 // from the finest to the coarsest. On each level, filtering and
1218 // SumBoundary are done as the last two things. So the communication
1219 // data on the sender side are always unfiltered and unsummed. The
1220 // receivers are responsible for filtering that is dependent on the grid
1221 // resolution. On the finest level, we coarsen the unsummed fp data onto
1222 // cp grids, which are the coarsened version of the fp grids with the
1223 // same DistributionMapping. Then on the level below, We use ParallelAdd
1224 // to add the finer level's cp data onto the current level's fp
1225 // data. After that, we apply filter and SumBoundary to the finer
1226 // level's cp MultiFab. At this time, the finer level's fp and cp data

Callers 1

DepositCurrentMethod · 0.80

Calls 6

UpdateCurrentNodalToStagFunction · 0.85
get_mr_levels_alldirsMethod · 0.80
nCompMethod · 0.80
hasMethod · 0.80
CoarsenFunction · 0.50
setValMethod · 0.45

Tested by

no test coverage detected