diff options
-rw-r--r-- | Examples/Modules/qed/breit_wheeler/bw_micro_table | bin | 0 -> 1152 bytes | |||
-rw-r--r-- | Examples/Modules/qed/breit_wheeler/inputs.3d_test_optical_depth_evolution | 163 | ||||
-rw-r--r-- | Examples/Modules/qed/quantum_synchrotron/inputs.3d_test_optical_depth_evolution | 115 | ||||
-rw-r--r-- | Source/Particles/MultiParticleContainer.H | 1 | ||||
-rw-r--r-- | Source/Particles/PhotonParticleContainer.H | 14 | ||||
-rw-r--r-- | Source/Particles/PhotonParticleContainer.cpp | 51 | ||||
-rw-r--r-- | Source/Particles/PhysicalParticleContainer.H | 38 | ||||
-rw-r--r-- | Source/Particles/PhysicalParticleContainer.cpp | 119 | ||||
-rw-r--r-- | Source/Particles/WarpXParticleContainer.H | 3 | ||||
-rw-r--r-- | Source/QED/BreitWheelerEngineWrapper.H | 8 | ||||
-rw-r--r-- | Source/QED/BreitWheelerEngineWrapper.cpp | 6 | ||||
-rw-r--r-- | Source/QED/QuantumSyncEngineWrapper.H | 10 | ||||
-rw-r--r-- | Source/QED/QuantumSyncEngineWrapper.cpp | 6 |
13 files changed, 513 insertions, 21 deletions
diff --git a/Examples/Modules/qed/breit_wheeler/bw_micro_table b/Examples/Modules/qed/breit_wheeler/bw_micro_table Binary files differnew file mode 100644 index 000000000..879675fc0 --- /dev/null +++ b/Examples/Modules/qed/breit_wheeler/bw_micro_table diff --git a/Examples/Modules/qed/breit_wheeler/inputs.3d_test_optical_depth_evolution b/Examples/Modules/qed/breit_wheeler/inputs.3d_test_optical_depth_evolution new file mode 100644 index 000000000..9d5d55eeb --- /dev/null +++ b/Examples/Modules/qed/breit_wheeler/inputs.3d_test_optical_depth_evolution @@ -0,0 +1,163 @@ +#An inputfile to demonstrate lookup table generation for the Breit Wheeler engine + +################################# +####### GENERAL PARAMETERS ###### +################################# +max_step = 10 +amr.n_cell = 64 64 64 +amr.max_grid_size = 32 # maximum size of each AMReX box, used to decompose the domain +amr.blocking_factor = 8 # minimum size of each AMReX box, used to decompose the domain +amr.plot_int = 10 +geometry.coord_sys = 0 # 0: Cartesian +geometry.is_periodic = 1 1 1 # Is periodic? +geometry.prob_lo = -1.e-6 -1.e-6 -1e-6 # physical domain +geometry.prob_hi = 1.e-6 1.e-6 1e6 +amr.max_level = 0 # Maximum level in hierarchy (1 might be unstable, >1 is not supported) + +################################# +############ NUMERICS ########### +################################# +algo.current_deposition = esirkepov +algo.charge_deposition = standard +algo.field_gathering = energy-conserving +algo.particle_pusher = boris +interpolation.nox = 3 # Particle interpolation order. Must be the same in x, y, and z +interpolation.noy = 3 +interpolation.noz = 3 +warpx.verbose = 1 +warpx.do_dive_cleaning = 0 +warpx.plot_raw_fields = 0 +warpx.plot_raw_fields_guards = 0 +warpx.plot_finepatch = 0 +warpx.plot_crsepatch = 0 +warpx.use_filter = 1 +warpx.cfl = 1. # if 1., the time step is set to its CFL limit +warpx.do_pml = 1 # use Perfectly Matched Layer as boundary condition +warpx.serialize_ics = 1 + +################################# +############ PLASMA ############# +################################# +particles.nspecies = 4 # number of species +particles.species_names = p1 p2 p3 p4 +particles.photon_species = p1 p2 p3 p4 +################################# + +p1.charge = -q_e +p1.mass = m_e +p1.injection_style = "NUniformPerCell" +p1.profile = "constant" +p1.xmin = -0.5e-6 +p1.ymin = -0.5e-6 +p1.zmin = -0.5e-6 +p1.xmax = 0.5e6 +p1.ymax = 0.5e6 +p1.zmax = 0.5e6 +p1.num_particles_per_cell_each_dim = 2 2 2 +p1.density = 1e19 +p1.profile = "constant" +p1.momentum_distribution_type = "gaussian" +p1.ux_m = 100.0 +p1.uy_m = 0.0 +p1.uz_m = 0.0 +p1.ux_th = 0. +p1.uy_th = 0. +p1.uz_th = 0. +##########QED#################### +p1.do_qed = 1 +p1.do_qed_breit_wheeler = 1 +################################# + +p2.charge = -q_e +p2.mass = m_e +p2.injection_style = "NUniformPerCell" +p2.profile = "constant" +p2.xmin = -0.5e-6 +p2.ymin = -0.5e-6 +p2.zmin = -0.5e-6 +p2.xmax = 0.5e6 +p2.ymax = 0.5e6 +p2.zmax = 0.5e6 +p2.num_particles_per_cell_each_dim = 2 2 2 +p2.density = 1e19 +p2.profile = "constant" +p2.momentum_distribution_type = "gaussian" +p2.ux_m = 0.0 +p2.uy_m = 1000.0 +p2.uz_m = 0.0 +p2.ux_th = 0. +p2.uy_th = 0. +p2.uz_th = 0. +##########QED#################### +p2.do_qed = 1 +p2.do_qed_breit_wheeler = 1 +################################# + +p3.charge = -q_e +p3.mass = m_e +p3.injection_style = "NUniformPerCell" +p3.profile = "constant" +p3.xmin = -0.5e-6 +p3.ymin = -0.5e-6 +p3.zmin = -0.5e-6 +p3.xmax = 0.5e6 +p3.ymax = 0.5e6 +p3.zmax = 0.5e6 +p3.num_particles_per_cell_each_dim = 2 2 2 +p3.density = 1e19 +p3.profile = "constant" +p3.momentum_distribution_type = "gaussian" +p3.ux_m = 0.0 +p3.uy_m = 0.0 +p3.uz_m = 10000.0 +p3.ux_th = 0. +p3.uy_th = 0. +p3.uz_th = 0. +##########QED#################### +p3.do_qed = 1 +p3.do_qed_breit_wheeler = 1 +################################# + +p4.charge = -q_e +p4.mass = m_e +p4.injection_style = "NUniformPerCell" +p4.profile = "constant" +p4.xmin = -0.5e-6 +p4.ymin = -0.5e-6 +p4.zmin = -0.5e-6 +p4.xmax = 0.5e6 +p4.ymax = 0.5e6 +p4.zmax = 0.5e6 +p4.num_particles_per_cell_each_dim = 2 2 2 +p4.density = 1e19 +p4.profile = "constant" +p4.momentum_distribution_type = "gaussian" +p4.ux_m = 57735.02691896 +p4.uy_m = 57735.02691896 +p4.uz_m = 57735.02691896 +p4.ux_th = 0. +p4.uy_th = 0. +p4.uz_th = 0. +##########QED#################### +p4.do_qed = 1 +p4.do_qed_breit_wheeler = 1 +################################# + +##########QED TABLES#################### +qed_bw.generate_table = 0 +#qed_bw.chi_min = 0.001 +#qed_bw.tab_dndt_chi_min = 0.1 +#qed_bw.tab_dndt_chi_max = 200 +#qed_bw.tab_dndt_how_many = 64 +#qed_bw.tab_pair_chi_min = 0.01 +#qed_bw.tab_pair_chi_max = 200 +#qed_bw.tab_pair_chi_how_many = 2 +#qed_bw.tab_pair_prob_how_many = 2 +#qed_bw.save_table_in = "bw_micro_table" +qed_bw.load_table_from = "bw_micro_table" +################################# + +### EXTERNAL FIELD ### (1e7 * [0.28571429 0.42857143 0.85714286] ) +warpx.B_external_particle = 2857142.85714286 4285714.28571428 8571428.57142857 +#### + diff --git a/Examples/Modules/qed/quantum_synchrotron/inputs.3d_test_optical_depth_evolution b/Examples/Modules/qed/quantum_synchrotron/inputs.3d_test_optical_depth_evolution new file mode 100644 index 000000000..45c7506f4 --- /dev/null +++ b/Examples/Modules/qed/quantum_synchrotron/inputs.3d_test_optical_depth_evolution @@ -0,0 +1,115 @@ +#An inputfile to demonstrate lookup table generation for the Breit Wheeler engine + +################################# +####### GENERAL PARAMETERS ###### +################################# +max_step = 300 +amr.n_cell = 128 128 +amr.max_grid_size = 32 # maximum size of each AMReX box, used to decompose the domain +amr.blocking_factor = 8 # minimum size of each AMReX box, used to decompose the domain +amr.plot_int = 158 +geometry.coord_sys = 0 # 0: Cartesian +geometry.is_periodic = 0 0 # Is periodic? +geometry.prob_lo = -32.e-6 -32.e-6 # physical domain +geometry.prob_hi = 32.e-6 32.e-6 +amr.max_level = 0 # Maximum level in hierarchy (1 might be unstable, >1 is not supported) +warpx.fine_tag_lo = -5.e-6 -35.e-6 +warpx.fine_tag_hi = 5.e-6 -25.e-6 + +################################# +############ NUMERICS ########### +################################# +algo.current_deposition = esirkepov +algo.charge_deposition = standard +algo.field_gathering = energy-conserving +algo.particle_pusher = boris +interpolation.nox = 3 # Particle interpolation order. Must be the same in x, y, and z +interpolation.noy = 3 +interpolation.noz = 3 +warpx.verbose = 1 +warpx.do_dive_cleaning = 0 +warpx.plot_raw_fields = 0 +warpx.plot_raw_fields_guards = 0 +warpx.plot_finepatch = 0 +warpx.plot_crsepatch = 0 +warpx.use_filter = 1 +warpx.cfl = 1. # if 1., the time step is set to its CFL limit +warpx.do_pml = 1 # use Perfectly Matched Layer as boundary condition +warpx.serialize_ics = 1 + +################################# +############ PLASMA ############# +################################# +particles.nspecies = 2 # number of species +particles.species_names = electrons positrons +################################# + +electrons.charge = -q_e +electrons.mass = m_e +electrons.injection_style = "NUniformPerCell" +electrons.profile = "constant" +electrons.xmin = -30e-6 +electrons.ymin = -30e-6 +electrons.zmin = -30e-6 +electrons.xmax = 30e-6 +electrons.ymax = 30e-6 +electrons.zmax = 30e-6 +electrons.num_particles_per_cell_each_dim = 2 2 +electrons.density = 1e19 +electrons.profile = "constant" +electrons.momentum_distribution_type = "gaussian" +electrons.ux_m = 0.0 +electrons.uy_m = 0.0 +electrons.uz_m = 0.0 +electrons.ux_th = 100. +electrons.uy_th = 100. +electrons.uz_th = 100. +##########QED#################### +electrons.do_qed = 1 +electrons.do_qed_quantum_sync = 1 +electrons.do_classical_radiation_reaction = 1 +################################# + +positrons.charge = q_e +positrons.mass = m_e +positrons.injection_style = "NUniformPerCell" +positrons.profile = "constant" +positrons.xmin = -30e-6 +positrons.ymin = -30e-6 +positrons.zmin = -30e-6 +positrons.xmax = 30e-6 +positrons.ymax = 30e-6 +positrons.zmax = 30e-6 +positrons.num_particles_per_cell_each_dim = 2 2 +positrons.density = 1e19 +positrons.profile = "constant" +positrons.momentum_distribution_type = "gaussian" +positrons.ux_m = 0.0 +positrons.uy_m = 0.0 +positrons.uz_m = 0.0 +positrons.ux_th = 100. +positrons.uy_th = 100. +positrons.uz_th = 100. +##########QED#################### +positrons.do_qed = 1 +positrons.do_qed_quantum_sync = 1 +positrons.do_classical_radiation_reaction = 1 +################################# + +##########QED TABLES#################### +qed_qs.chi_min = 0.001 +qed_qs.generate_table = 1 +qed_qs.tab_dndt_chi_min = 0.001 +qed_qs.tab_dndt_chi_max = 200 +qed_qs.tab_dndt_how_many = 200 +qed_qs.tab_em_chi_min = 0.001 +qed_qs.tab_em_chi_max = 200 +qed_qs.tab_em_chi_how_many = 2 +qed_qs.tab_em_prob_how_many = 2 +qed_qs.save_table_in = "qs_table" +#qed_qs.load_table_from = "qs_table" +################################# + +### EXTERNAL FIELD ### +warpx.B_external_particle = 0 0 1.0e7 +#### diff --git a/Source/Particles/MultiParticleContainer.H b/Source/Particles/MultiParticleContainer.H index f9a0e51d7..06898a5c1 100644 --- a/Source/Particles/MultiParticleContainer.H +++ b/Source/Particles/MultiParticleContainer.H @@ -11,6 +11,7 @@ #include <AMReX_Particles.H> #ifdef WARPX_QED + #include <QedChiFunctions.H> #include <BreitWheelerEngineWrapper.H> #include <QuantumSyncEngineWrapper.H> #endif diff --git a/Source/Particles/PhotonParticleContainer.H b/Source/Particles/PhotonParticleContainer.H index 851726d57..580f13f86 100644 --- a/Source/Particles/PhotonParticleContainer.H +++ b/Source/Particles/PhotonParticleContainer.H @@ -46,7 +46,7 @@ public: amrex::Gpu::ManagedDeviceVector<amrex::ParticleReal>& zp, amrex::Real dt, DtType a_dt_type=DtType::Full) override; - // Don't push momenta for photons + // Do nothing virtual void PushP (int lev, amrex::Real dt, const amrex::MultiFab& Ex, @@ -79,6 +79,18 @@ public: return false; }; +#ifdef WARPX_QED + /** + * This function evolves the optical depth of the photons if QED effects + * are enabled. + * @param[in,out] pti particle iterator (optical depth will be modified) + * @param[in] dt temporal step + */ + virtual void EvolveOpticalDepth(WarpXParIter& pti, + amrex::Real dt) override; + +#endif + }; #endif // #ifndef WARPX_PhotonParticleContainer_H_ diff --git a/Source/Particles/PhotonParticleContainer.cpp b/Source/Particles/PhotonParticleContainer.cpp index fd47ac8a0..424569c9a 100644 --- a/Source/Particles/PhotonParticleContainer.cpp +++ b/Source/Particles/PhotonParticleContainer.cpp @@ -78,8 +78,6 @@ PhotonParticleContainer::PushPX(WarpXParIter& pti, copy_attribs(pti, x, y, z); } - //No need to update momentum for photons (for now) - amrex::ParallelFor( pti.numParticles(), [=] AMREX_GPU_DEVICE (long i) { @@ -88,7 +86,6 @@ PhotonParticleContainer::PushPX(WarpXParIter& pti, ux[i], uy[i], uz[i], dt ); } ); - } void @@ -116,3 +113,51 @@ PhotonParticleContainer::Evolve (int lev, t, dt); } + +#ifdef WARPX_QED + +void +PhotonParticleContainer::EvolveOpticalDepth( + WarpXParIter& pti,amrex::Real dt) +{ + //m_shr_p_bw_engine->are_lookup_tables_initialized() is necessary here if we want + //to perform just initialization tests of the optical depth without actually + //enabling QED effects (this requires lookup tables). + if(!has_breit_wheeler() || !m_shr_p_bw_engine->are_lookup_tables_initialized()) + return; + + auto& attribs = pti.GetAttribs(); + ParticleReal* const AMREX_RESTRICT ux = attribs[PIdx::ux].dataPtr(); + ParticleReal* const AMREX_RESTRICT uy = attribs[PIdx::uy].dataPtr(); + ParticleReal* const AMREX_RESTRICT uz = attribs[PIdx::uz].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ex = attribs[PIdx::Ex].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ey = attribs[PIdx::Ey].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ez = attribs[PIdx::Ez].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Bx = attribs[PIdx::Bx].dataPtr(); + const ParticleReal* const AMREX_RESTRICT By = attribs[PIdx::By].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Bz = attribs[PIdx::Bz].dataPtr(); + + BreitWheelerEvolveOpticalDepth evolve_opt = + m_shr_p_bw_engine->build_evolve_functor(); + + amrex::Real* AMREX_RESTRICT p_tau = + pti.GetAttribs(particle_comps["tau"]).dataPtr(); + + const auto me = PhysConst::m_e; + + amrex::ParallelFor( + pti.numParticles(), + [=] AMREX_GPU_DEVICE (long i) { + const ParticleReal px = me * ux[i]; + const ParticleReal py = me * uy[i]; + const ParticleReal pz = me * uz[i]; + + bool has_event_happened = evolve_opt( + px, py, pz, + Ex[i], Ey[i], Ez[i], + Bx[i], By[i], Bz[i], + dt, p_tau[i]); + } + ); +} +#endif diff --git a/Source/Particles/PhysicalParticleContainer.H b/Source/Particles/PhysicalParticleContainer.H index 174488eb9..e70b470b8 100644 --- a/Source/Particles/PhysicalParticleContainer.H +++ b/Source/Particles/PhysicalParticleContainer.H @@ -187,13 +187,47 @@ public: amrex::FArrayBox const * & byfab, amrex::FArrayBox const * & bzfab); #ifdef WARPX_QED + //Functions decleared in WarpXParticleContainer.H + //containers for which QED processes could be relevant + //are expected to override these functions + + /** + * Tells if this PhysicalParticleContainer has Quantum + * Synchrotron process enabled + * @return true if process is enabled + */ bool has_quantum_sync() override; + + /** + * Tells if this PhysicalParticleContainer has Breit + * Wheeler process enabled + * @return true if process is enabled + */ bool has_breit_wheeler() override; + /** + * Acquires a shared smart pointer to a BreitWheelerEngine + * @param[in] ptr the pointer + */ void set_breit_wheeler_engine_ptr - (std::shared_ptr<BreitWheelerEngine>) override; + (std::shared_ptr<BreitWheelerEngine> ptr) override; + + /** + * Acquires a shared smart pointer to a QuantumSynchrotronEngine + * @param[in] ptr the pointer + */ void set_quantum_sync_engine_ptr - (std::shared_ptr<QuantumSynchrotronEngine>) override; + (std::shared_ptr<QuantumSynchrotronEngine> ptr) override; + //__________ + + /** + * This function evolves the optical depth of the particles if QED effects + * are enabled. + * @param[in,out] pti particle iterator (optical depth will be modified) + * @param[in] dt temporal step + */ + virtual void EvolveOpticalDepth(WarpXParIter& pti, + amrex::Real dt); #endif protected: diff --git a/Source/Particles/PhysicalParticleContainer.cpp b/Source/Particles/PhysicalParticleContainer.cpp index 938c80de5..9c13d34e1 100644 --- a/Source/Particles/PhysicalParticleContainer.cpp +++ b/Source/Particles/PhysicalParticleContainer.cpp @@ -1052,6 +1052,7 @@ PhysicalParticleContainer::Evolve (int lev, BL_PROFILE("PPC::Evolve()"); BL_PROFILE_VAR_NS("PPC::Evolve::Copy", blp_copy); BL_PROFILE_VAR_NS("PPC::FieldGather", blp_fg); + BL_PROFILE_VAR_NS("PPC::EvolveOpticalDepth", blp_ppc_qed_ev); BL_PROFILE_VAR_NS("PPC::ParticlePush", blp_ppc_pp); const std::array<Real,3>& dx = WarpX::CellSize(lev); @@ -1243,6 +1244,15 @@ PhysicalParticleContainer::Evolve (int lev, BL_PROFILE_VAR_STOP(blp_fg); +#ifdef WARPX_QED + // + //Evolve Optical Depth + // + BL_PROFILE_VAR_START(blp_ppc_qed_ev); + EvolveOpticalDepth(pti, dt); + BL_PROFILE_VAR_STOP(blp_ppc_qed_ev); +#endif + // // Particle Push // @@ -1590,8 +1600,45 @@ PhysicalParticleContainer::PushPX(WarpXParIter& pti, const Real q = this->charge; const Real m = this-> mass; +#ifdef WARPX_QED - //Assumes that all consistency checks have been done at initialization + auto t_chi_max = m_shr_p_qs_engine->get_ref_ctrl().chi_part_min; + + if(do_classical_radiation_reaction){ + if(m_do_qed_quantum_sync){ + amrex::ParallelFor( + pti.numParticles(), + [=] AMREX_GPU_DEVICE (long i) { + auto chi = QedUtils::chi_lepton(m*ux[i], m*uy[i], m*uz[i], + Ex[i], Ey[i], Ez[i], + Bx[i], By[i], Bz[i]); + if(chi < t_chi_max){ + UpdateMomentumBorisWithRadiationReaction( ux[i], uy[i], uz[i], + Ex[i], Ey[i], Ez[i], Bx[i], + By[i], Bz[i], q, m, dt); + } + else{ + UpdateMomentumBoris( ux[i], uy[i], uz[i], + Ex[i], Ey[i], Ez[i], Bx[i], + By[i], Bz[i], q, m, dt); + } + UpdatePosition( x[i], y[i], z[i], + ux[i], uy[i], uz[i], dt ); + } + ); + }else{ + amrex::ParallelFor( + pti.numParticles(), + [=] AMREX_GPU_DEVICE (long i) { + UpdateMomentumBorisWithRadiationReaction( ux[i], uy[i], uz[i], + Ex[i], Ey[i], Ez[i], Bx[i], + By[i], Bz[i], q, m, dt); + UpdatePosition( x[i], y[i], z[i], + ux[i], uy[i], uz[i], dt ); + } + ); + } +#else if(do_classical_radiation_reaction){ amrex::ParallelFor( pti.numParticles(), @@ -1605,6 +1652,7 @@ PhysicalParticleContainer::PushPX(WarpXParIter& pti, ux[i], uy[i], uz[i], dt ); } ); +#endif } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::Boris){ amrex::ParallelFor( pti.numParticles(), @@ -1649,6 +1697,52 @@ PhysicalParticleContainer::PushPX(WarpXParIter& pti, }; } +#ifdef WARPX_QED +void PhysicalParticleContainer::EvolveOpticalDepth( + WarpXParIter& pti, amrex::Real dt) +{ + //m_shr_p_qs_engine->are_lookup_tables_initialized() is necessary here if we want + //to perform just initialization tests of the optical depth without actually + //enabling QED effects (this requires lookup tables). + if(!has_quantum_sync() || !m_shr_p_qs_engine->are_lookup_tables_initialized()) + return; + + QuantumSynchrotronEvolveOpticalDepth evolve_opt = + m_shr_p_qs_engine->build_evolve_functor(); + + auto& attribs = pti.GetAttribs(); + const ParticleReal* const AMREX_RESTRICT ux = attribs[PIdx::ux].dataPtr(); + const ParticleReal* const AMREX_RESTRICT uy = attribs[PIdx::uy].dataPtr(); + const ParticleReal* const AMREX_RESTRICT uz = attribs[PIdx::uz].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ex = attribs[PIdx::Ex].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ey = attribs[PIdx::Ey].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Ez = attribs[PIdx::Ez].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Bx = attribs[PIdx::Bx].dataPtr(); + const ParticleReal* const AMREX_RESTRICT By = attribs[PIdx::By].dataPtr(); + const ParticleReal* const AMREX_RESTRICT Bz = attribs[PIdx::Bz].dataPtr(); + + ParticleReal* const AMREX_RESTRICT p_tau = + pti.GetAttribs(particle_comps["tau"]).dataPtr(); + + const ParticleReal m = this->mass; + + amrex::ParallelFor(pti.numParticles(), + [=] AMREX_GPU_DEVICE (long i) { + const ParticleReal px = m * ux[i]; + const ParticleReal py = m * uy[i]; + const ParticleReal pz = m * uz[i]; + + bool has_event_happened = evolve_opt( + px, py, pz, + Ex[i], Ey[i], Ez[i], + Bx[i], By[i], Bz[i], + dt, p_tau[i]); + } + ); + +} +#endif + void PhysicalParticleContainer::PushP (int lev, Real dt, const MultiFab& Ex, const MultiFab& Ey, const MultiFab& Ez, @@ -1732,12 +1826,10 @@ PhysicalParticleContainer::PushP (int lev, Real dt, ion_lev = pti.GetiAttribs(particle_icomps["ionization_level"]).dataPtr(); } - //Assumes that all consistency checks have been done at initialization if(do_classical_radiation_reaction){ - amrex::ParallelFor( - pti.numParticles(), - [=] AMREX_GPU_DEVICE (long i) { + amrex::ParallelFor(pti.numParticles(), + [=] AMREX_GPU_DEVICE (long i){ Real qp = q; if (ion_lev){ qp *= ion_lev[i]; } UpdateMomentumBorisWithRadiationReaction( @@ -1748,7 +1840,7 @@ PhysicalParticleContainer::PushP (int lev, Real dt, } ); } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::Boris){ - amrex::ParallelFor( pti.numParticles(), + amrex::ParallelFor(pti.numParticles(), [=] AMREX_GPU_DEVICE (long i) { Real qp = q; if (ion_lev){ qp *= ion_lev[i]; } @@ -1759,8 +1851,8 @@ PhysicalParticleContainer::PushP (int lev, Real dt, qp, m, dt); } ); - } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::Vay) { - amrex::ParallelFor( pti.numParticles(), + } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::Vay){ + amrex::ParallelFor(pti.numParticles(), [=] AMREX_GPU_DEVICE (long i) { Real qp = q; if (ion_lev){ qp *= ion_lev[i]; } @@ -1771,16 +1863,19 @@ PhysicalParticleContainer::PushP (int lev, Real dt, qp, m, dt); } ); - } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::HigueraCary) { - amrex::ParallelFor( pti.numParticles(), + } else if (WarpX::particle_pusher_algo == ParticlePusherAlgo::HigueraCary){ + amrex::ParallelFor(pti.numParticles(), [=] AMREX_GPU_DEVICE (long i) { UpdateMomentumHigueraCary( ux[i], uy[i], uz[i], - Expp[i], Eypp[i], Ezpp[i], Bxpp[i], Bypp[i], Bzpp[i], q, m, dt); + Expp[i], Eypp[i], Ezpp[i], + Bxpp[i], Bypp[i], Bzpp[i], + q, m, dt); } ); } else { amrex::Abort("Unknown particle pusher"); - }; + } + } } } diff --git a/Source/Particles/WarpXParticleContainer.H b/Source/Particles/WarpXParticleContainer.H index 7f86930b2..1a89ded02 100644 --- a/Source/Particles/WarpXParticleContainer.H +++ b/Source/Particles/WarpXParticleContainer.H @@ -322,9 +322,12 @@ protected: #ifdef WARPX_QED bool m_do_qed = false; + //Species for which QED effects are relevant should override these methods virtual bool has_quantum_sync(){return false;}; virtual bool has_breit_wheeler(){return false;}; + //Species can receive a shared pointer to a QED engine (species for + //which this is relevant should override these functions) virtual void set_breit_wheeler_engine_ptr(std::shared_ptr<BreitWheelerEngine>){}; virtual void diff --git a/Source/QED/BreitWheelerEngineWrapper.H b/Source/QED/BreitWheelerEngineWrapper.H index 1033ff7c9..3cdfdeae6 100644 --- a/Source/QED/BreitWheelerEngineWrapper.H +++ b/Source/QED/BreitWheelerEngineWrapper.H @@ -151,7 +151,7 @@ class BreitWheelerGeneratePairs { public: /** - * Constructor acquires a reference to control parameters and + * Constructor acquires pointers to control parameters and * lookup tables data. * lookup_table uses non-owning vectors under the hood. So no new data * allocations should be triggered on GPU @@ -288,6 +288,12 @@ public: */ PicsarBreitWheelerCtrl get_default_ctrl() const; + /** + * returns a constant reference to the control parameters + * @return const reference to control parameters + */ + const PicsarBreitWheelerCtrl& get_ref_ctrl() const; + private: bool m_lookup_tables_initialized = false; diff --git a/Source/QED/BreitWheelerEngineWrapper.cpp b/Source/QED/BreitWheelerEngineWrapper.cpp index 42953c97f..78ff13fc5 100644 --- a/Source/QED/BreitWheelerEngineWrapper.cpp +++ b/Source/QED/BreitWheelerEngineWrapper.cpp @@ -176,6 +176,12 @@ BreitWheelerEngine::get_default_ctrl() const return PicsarBreitWheelerCtrl(); } +const PicsarBreitWheelerCtrl& +BreitWheelerEngine::get_ref_ctrl() const +{ + return m_innards.ctrl; +} + void BreitWheelerEngine::compute_lookup_tables ( PicsarBreitWheelerCtrl ctrl) { diff --git a/Source/QED/QuantumSyncEngineWrapper.H b/Source/QED/QuantumSyncEngineWrapper.H index 1a6ffe4f3..fd1571720 100644 --- a/Source/QED/QuantumSyncEngineWrapper.H +++ b/Source/QED/QuantumSyncEngineWrapper.H @@ -79,7 +79,7 @@ class QuantumSynchrotronEvolveOpticalDepth { public: /** - * Constructor acquires a reference to control parameters and + * Constructor acquires pointers to control parameters and * lookup tables data. * lookup_table uses non-owning vectors under the hood. So no new data * allocations should be triggered on GPU @@ -152,7 +152,7 @@ class QuantumSynchrotronGeneratePhotonAndUpdateMomentum { public: /** - * Constructor acquires a reference to control parameters and + * Constructor acquires pointers to control parameters and * lookup tables data. * lookup_table uses non-owning vectors under the hood. So no new data * allocations should be triggered on GPU @@ -285,6 +285,12 @@ public: */ PicsarQuantumSynchrotronCtrl get_default_ctrl() const; + /** + * returns a constant reference to the control parameters + * @return const reference to control parameters + */ + const PicsarQuantumSynchrotronCtrl& get_ref_ctrl() const; + private: bool m_lookup_tables_initialized = false; diff --git a/Source/QED/QuantumSyncEngineWrapper.cpp b/Source/QED/QuantumSyncEngineWrapper.cpp index b2630dc4d..c2d9f0abf 100644 --- a/Source/QED/QuantumSyncEngineWrapper.cpp +++ b/Source/QED/QuantumSyncEngineWrapper.cpp @@ -175,6 +175,12 @@ QuantumSynchrotronEngine::get_default_ctrl() const return PicsarQuantumSynchrotronCtrl(); } +const PicsarQuantumSynchrotronCtrl& +QuantumSynchrotronEngine::get_ref_ctrl() const +{ + return m_innards.ctrl; +} + void QuantumSynchrotronEngine::compute_lookup_tables ( PicsarQuantumSynchrotronCtrl ctrl) { |