22#include "shamrock/legacy/patch/interfaces/interface_handler.hpp"
23#include "shamrock/legacy/patch/interfaces/interface_selector.hpp"
26#include "shammodels/sph/legacy/algs/smoothing_length_impl.hpp"
27#include "shamrock/legacy/patch/utility/merged_patch.hpp"
30#include "shamrock/sph/kernels.hpp"
31#include "shamrock/sph/sphpart.hpp"
35namespace models::sph {
38 template<
class flt,
class morton_prec,
class Kernel>
39 class SmoothinglengthCompute {
41 using vec = sycl::vec<flt, 3>;
53 SmoothinglengthCompute(
59 this->htol_up_tol = htol_up_tol;
60 this->htol_up_iter = htol_up_iter;
63 inline void iterate_smoothing_length(
72 shamrock::patch::PatchData &pdat_merge,
73 sycl::buffer<flt> &hnew,
74 sycl::buffer<flt> &omega,
75 sycl::buffer<flt> &eps_h) {
79 impl::sycl_init_h_iter_bufs(
80 queue, or_element_cnt, ihpart, pdat_merge, hnew, omega, eps_h);
82 for (
u32 it_num = 0; it_num < 30; it_num++) {
130 inline void iterate_smoothing_length(
138 PatchDataBuffer & pdat_buf_merge,
139 sycl::buffer<flt> & hnew,
140 sycl::buffer<flt> & omega,
141 sycl::buffer<flt> & eps_h){
143 auto timer = timings::start_timer(
"iterate_smoothing_length",timings::function);
145 impl::sycl_init_h_iter_bufs(queue, or_element_cnt,ihpart, pdat_buf_merge, hnew, omega, eps_h);
147 for (
u32 it_num = 0 ; it_num < 30; it_num++) {
193 template<
class flt,
class u_morton,
class Kernel>
194 inline void compute_smoothing_length(
199 flt sph_gpart_mass) {
201 using namespace shamrock::patch;
203 using vec = sycl::vec<flt, 3>;
207 const flt loc_htol_up_tol = htol_up_tol;
208 const flt loc_htol_up_iter = htol_up_iter;
210 const u32 ixyz = sched.pdl.get_field_idx<vec>(
"xyz");
211 const u32 ihpart = sched.pdl.get_field_idx<flt>(
"hpart");
220 sched.compute_patch_field(
223 [loc_htol_up_tol](sycl::queue &queue,
Patch &p, PatchData &pdat) {
224 return patchdata::sph::get_h_max<flt>(pdat.pdl, queue, pdat) * loc_htol_up_tol
229 LegacyInterfacehandler<vec, flt> interface_hndl;
230 interface_hndl.template compute_interface_list<InterfaceSelector_SPH<vec, flt>>(
231 sched, sptree, h_field, periodic_mode);
232 interface_hndl.comm_interfaces(sched, periodic_mode);
235 std::unordered_map<u64, MergedPatchData<flt>> merge_pdat
239 std::unordered_map<u64, std::unique_ptr<RadixTree<u_morton, vec>>> radix_trees;
240 std::unordered_map<u64, std::unique_ptr<RadixTreeField<flt>>> cell_int_rads;
242 constexpr u32 reduc_level = 5;
244 sched.for_each_patch([&](
u64 id_patch,
const Patch & ) {
245 shamlog_debug_ln(
"SPHLeapfrog",
"patch : n", id_patch,
"->",
"making Radix Tree");
247 if (merge_pdat.at(id_patch).or_element_cnt == 0)
249 "SPHLeapfrog",
"patch : n", id_patch,
"->",
"is empty skipping tree build");
252 PatchData &mpdat = merge_pdat.at(id_patch).data;
254 auto &buf_xyz = mpdat.get_field<vec>(ixyz).get_buf();
256 std::tuple<vec, vec> &box = merge_pdat.at(id_patch).box;
259 radix_trees[id_patch] = std::make_unique<RadixTree<u_morton, vec>>(
267 sched.for_each_patch([&](
u64 id_patch,
Patch ) {
269 "SPHLeapfrog",
"patch : n", id_patch,
"->",
"compute radix tree cell volumes");
270 if (merge_pdat.at(id_patch).or_element_cnt == 0)
276 "is empty skipping tree volumes step");
278 radix_trees[id_patch]->compute_cell_ibounding_box(
283 sched.for_each_patch([&](
u64 id_patch,
Patch ) {
289 "compute Radix Tree interaction boxes");
290 if (merge_pdat.at(id_patch).or_element_cnt == 0)
296 "is empty skipping interaction box compute");
298 PatchData &mpdat = merge_pdat.at(id_patch).data;
300 auto &buf_h = mpdat.get_field<flt>(ihpart).get_buf();
302 cell_int_rads[id_patch] = std::make_unique<RadixTreeField<flt>>(
303 radix_trees[id_patch]->compute_int_boxes(
308 std::cout <<
"making omega field" << std::endl;
309 PatchComputeField<flt> hnew_field;
310 PatchComputeField<flt> omega_field;
312 hnew_field.generate(sched);
313 omega_field.generate(sched);
316 sched.for_each_patch([&](
u64 id_patch, Patch cur_p) {
317 shamlog_debug_ln(
"SPHLeapfrog",
"patch : n", id_patch,
"->",
"Init h iteration");
318 if (merge_pdat.at(id_patch).or_element_cnt == 0)
324 "is empty skipping h iteration");
326 PatchData &pdat_merge = merge_pdat.at(id_patch).data;
328 auto &hnew = hnew_field.get_buf(id_patch);
329 auto &
omega = omega_field.get_buf(id_patch);
330 sycl::buffer<flt>
eps_h = sycl::buffer<flt>(merge_pdat.at(id_patch).or_element_cnt);
332 sycl::range range_npart{merge_pdat.at(id_patch).or_element_cnt};
336 "merging -> original size :",
337 merge_pdat.at(id_patch).or_element_cnt,
339 pdat_merge.get_obj_cnt());
342 sched.pdl, htol_up_tol, htol_up_iter);
344 h_iterator.iterate_smoothing_length(
345 shamsys::instance::get_compute_queue(),
346 merge_pdat.at(id_patch).or_element_cnt,
348 *radix_trees[id_patch],
349 *cell_int_rads[id_patch],
357 auto h_new = hnew->template get_access<sycl::access::mode::read>(cgh);
359 auto acc_hpart = pdat_merge.get_field<flt>(ihpart)
361 ->template get_access<sycl::access::mode::write>(cgh);
363 cgh.parallel_for(range_npart, [=](sycl::item<1> item) {
364 acc_hpart[item] =
h_new[item];
370 write_back_merge_patches(sched, merge_pdat);
constexpr const char * eps_h
Epsilon h references (for h-iteration convergence).
constexpr const char * h_new
New smoothing length references (for h-iteration).
constexpr const char * omega
Grad-h correction factor \Omega.
sycl::queue & get_compute_queue(u32 id=0)
float f32
Alias for float.
std::uint32_t u32
32 bit unsigned integer
std::uint64_t u64
64 bit unsigned integer
PatchTree patch_tree
handle the tree structure of the patches
Define a field attached to a patch (example: FMM multipoles, hmax in SPH).
u32 get_field_idx(const std::string &field_name) const
Get the field id if matching name & type.
PatchCoordTransform< T > get_patch_transform() const
Get a PatchCoordTransform object that describes the conversion between patch coordinates and domain c...
header for PatchData related function and declaration
shambase::details::BasicStackEntry StackEntry
Alias for shambase::details::BasicStackEntry.
Patch object that contain generic patch information.