aboutsummaryrefslogtreecommitdiff
path: root/Source/Particles/WarpXParticleContainer.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'Source/Particles/WarpXParticleContainer.cpp')
-rw-r--r--Source/Particles/WarpXParticleContainer.cpp102
1 files changed, 74 insertions, 28 deletions
diff --git a/Source/Particles/WarpXParticleContainer.cpp b/Source/Particles/WarpXParticleContainer.cpp
index abb2a224c..564ffa706 100644
--- a/Source/Particles/WarpXParticleContainer.cpp
+++ b/Source/Particles/WarpXParticleContainer.cpp
@@ -499,6 +499,47 @@ WarpXParticleContainer::DepositCurrent (WarpXParIter& pti,
#endif
}
+void
+WarpXParticleContainer::DepositCurrent (
+ amrex::Vector<std::array< std::unique_ptr<amrex::MultiFab>, 3 > >& J,
+ const amrex::Real dt, const amrex::Real relative_t)
+{
+ // Loop over the refinement levels
+ int const finest_level = J.size() - 1;
+ for (int lev = 0; lev <= finest_level; ++lev)
+ {
+ // Loop over particle tiles and deposit current on each level
+#ifdef AMREX_USE_OMP
+#pragma omp parallel if (amrex::Gpu::notInLaunchRegion())
+ {
+ int thread_num = omp_get_thread_num();
+#else
+ int thread_num = 0;
+#endif
+ for (WarpXParIter pti(*this, lev); pti.isValid(); ++pti)
+ {
+ const long np = pti.numParticles();
+ const auto & wp = pti.GetAttribs(PIdx::w);
+ const auto & uxp = pti.GetAttribs(PIdx::ux);
+ const auto & uyp = pti.GetAttribs(PIdx::uy);
+ const auto & uzp = pti.GetAttribs(PIdx::uz);
+
+ int* AMREX_RESTRICT ion_lev = nullptr;
+ if (do_field_ionization)
+ {
+ ion_lev = pti.GetiAttribs(particle_icomps["ionization_level"]).dataPtr();
+ }
+
+ DepositCurrent(pti, wp, uxp, uyp, uzp, ion_lev,
+ J[lev][0].get(), J[lev][1].get(), J[lev][2].get(),
+ 0, np, thread_num, lev, lev, dt, relative_t/dt);
+ }
+#ifdef AMREX_USE_OMP
+ }
+#endif
+ }
+}
+
/* \brief Charge Deposition for thread thread_num
* \param pti : Particle iterator
* \param wp : Array of particle weights
@@ -666,18 +707,21 @@ WarpXParticleContainer::DepositCharge (WarpXParIter& pti, RealVector& wp,
void
WarpXParticleContainer::DepositCharge (amrex::Vector<std::unique_ptr<amrex::MultiFab> >& rho,
- bool local, bool reset,
- bool do_rz_volume_scaling)
+ const bool local, const bool reset,
+ const bool do_rz_volume_scaling,
+ const bool interpolate_across_levels,
+ const int icomp)
{
#ifdef WARPX_DIM_RZ
(void)do_rz_volume_scaling;
#endif
// Loop over the refinement levels
int const finest_level = rho.size() - 1;
- for (int lev = 0; lev <= finest_level; ++lev) {
-
- // Reset the `rho` array if `reset` is True
- if (reset) rho[lev]->setVal(0.0, rho[lev]->nGrowVect());
+ for (int lev = 0; lev <= finest_level; ++lev)
+ {
+ // Reset the rho array if reset is True
+ int const nc = WarpX::ncomps;
+ if (reset) rho[lev]->setVal(0., icomp*nc, nc, rho[lev]->nGrowVect());
// Loop over particle tiles and deposit charge on each level
#ifdef AMREX_USE_OMP
@@ -692,21 +736,21 @@ WarpXParticleContainer::DepositCharge (amrex::Vector<std::unique_ptr<amrex::Mult
const long np = pti.numParticles();
auto& wp = pti.GetAttribs(PIdx::w);
- int* AMREX_RESTRICT ion_lev;
- if (do_field_ionization){
+ int* AMREX_RESTRICT ion_lev = nullptr;
+ if (do_field_ionization)
+ {
ion_lev = pti.GetiAttribs(particle_icomps["ionization_level"]).dataPtr();
- } else {
- ion_lev = nullptr;
}
- DepositCharge(pti, wp, ion_lev, rho[lev].get(), 0, 0, np, thread_num, lev, lev);
+ DepositCharge(pti, wp, ion_lev, rho[lev].get(), icomp, 0, np, thread_num, lev, lev);
}
#ifdef AMREX_USE_OMP
}
#endif
#ifdef WARPX_DIM_RZ
- if (do_rz_volume_scaling) {
+ if (do_rz_volume_scaling)
+ {
WarpX::GetInstance().ApplyInverseVolumeScalingToChargeDensity(rho[lev].get(), lev);
}
#else
@@ -714,22 +758,24 @@ WarpXParticleContainer::DepositCharge (amrex::Vector<std::unique_ptr<amrex::Mult
#endif
// Exchange guard cells
- if (!local) rho[lev]->SumBoundary( m_gdb->Geom(lev).periodicity() );
+ if (local == false) rho[lev]->SumBoundary(m_gdb->Geom(lev).periodicity());
}
// Now that the charge has been deposited at each level,
// we average down from fine to crse
- for (int lev = finest_level - 1; lev >= 0; --lev) {
- const DistributionMapping& fine_dm = rho[lev+1]->DistributionMap();
- BoxArray coarsened_fine_BA = rho[lev+1]->boxArray();
- coarsened_fine_BA.coarsen(m_gdb->refRatio(lev));
- MultiFab coarsened_fine_data(coarsened_fine_BA, fine_dm, rho[lev+1]->nComp(), 0);
- coarsened_fine_data.setVal(0.0);
-
- int const refinement_ratio = 2;
-
- CoarsenMR::Coarsen( coarsened_fine_data, *rho[lev+1], IntVect(refinement_ratio) );
- rho[lev]->ParallelAdd( coarsened_fine_data, m_gdb->Geom(lev).periodicity() );
+ if (interpolate_across_levels)
+ {
+ for (int lev = finest_level - 1; lev >= 0; --lev)
+ {
+ const DistributionMapping& fine_dm = rho[lev+1]->DistributionMap();
+ BoxArray coarsened_fine_BA = rho[lev+1]->boxArray();
+ coarsened_fine_BA.coarsen(m_gdb->refRatio(lev));
+ MultiFab coarsened_fine_data(coarsened_fine_BA, fine_dm, rho[lev+1]->nComp(), 0);
+ coarsened_fine_data.setVal(0.0);
+ const int refinement_ratio = 2;
+ CoarsenMR::Coarsen(coarsened_fine_data, *rho[lev+1], IntVect(refinement_ratio));
+ rho[lev]->ParallelAdd(coarsened_fine_data, m_gdb->Geom(lev).periodicity());
+ }
}
}
@@ -789,7 +835,7 @@ WarpXParticleContainer::GetChargeDensity (int lev, bool local)
WarpX::GetInstance().ApplyInverseVolumeScalingToChargeDensity(rho.get(), lev);
#endif
- if (!local) rho->SumBoundary(gm.periodicity());
+ if (local == false) rho->SumBoundary(gm.periodicity());
return rho;
}
@@ -814,7 +860,7 @@ Real WarpXParticleContainer::sumParticleCharge(bool local) {
}
}
- if (!local) ParallelDescriptor::ReduceRealSum(total_charge);
+ if (local == false) ParallelDescriptor::ReduceRealSum(total_charge);
total_charge *= this->charge;
return total_charge;
}
@@ -890,7 +936,7 @@ std::array<Real, 3> WarpXParticleContainer::meanParticleVelocity(bool local) {
}
}
- if (!local) {
+ if (local == false) {
ParallelDescriptor::ReduceRealSum(vx_total);
ParallelDescriptor::ReduceRealSum(vy_total);
ParallelDescriptor::ReduceRealSum(vz_total);
@@ -929,7 +975,7 @@ Real WarpXParticleContainer::maxParticleVelocity(bool local) {
}
}
- if (!local) ParallelAllReduce::Max(max_v, ParallelDescriptor::Communicator());
+ if (local == false) ParallelAllReduce::Max(max_v, ParallelDescriptor::Communicator());
return max_v;
}