Shamrock 2025.10.0
Astrophysical Code
Loading...
Searching...
No Matches
VTKDump.cpp
Go to the documentation of this file.
1// -------------------------------------------------------//
2//
3// SHAMROCK code for hydrodynamics
4// Copyright (c) 2021-2026 Timothée David--Cléris <tim.shamrock@proton.me>
5// SPDX-License-Identifier: CeCILL Free Software License Agreement v2.1
6// Shamrock is licensed under the CeCILL 2.1 License, see LICENSE for more information
7//
8// -------------------------------------------------------//
9
18
26
27// Use shared VTK dump utilities
33
35
36 template<class Tvec, template<class> class SPHKernel>
37 void VTKDump<Tvec, SPHKernel>::do_dump(std::string filename, bool add_patch_world_id) {
38
39 StackEntry stack_loc{};
40
41 using namespace shamrock;
42 using namespace shamrock::patch;
43 shamrock::SchedulerUtility utility(scheduler());
44
45 PatchDataLayerLayout &pdl = scheduler().pdl_old();
46 const u32 ixyz = pdl.get_field_idx<Tvec>("xyz");
47 const u32 ivxyz = pdl.get_field_idx<Tvec>("vxyz");
48 const u32 iaxyz = pdl.get_field_idx<Tvec>("axyz");
49 const u32 iuint = pdl.get_field_idx<Tscal>("uint");
50 const u32 iduint = pdl.get_field_idx<Tscal>("duint");
51 const u32 ihpart = pdl.get_field_idx<Tscal>("hpart");
52 ComputeField<Tscal> density = utility.make_compute_field<Tscal>("rho", 1);
53
54 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
55 shamlog_debug_ln("sph::vtk", "compute rho field for patch ", p.id_patch);
56
57 auto &buf_hpart = pdat.get_field<Tscal>(ihpart).get_buf();
58
59 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
60 auto &q = sptr->get_queue();
61
62 sham::EventList depends_list;
63 const Tscal *acc_h = buf_hpart.get_read_access(depends_list);
64 auto acc_rho = density.get_buf(p.id_patch).get_write_access(depends_list);
65
66 auto e = q.submit(depends_list, [&](sycl::handler &cgh) {
67 const Tscal part_mass = solver_config.gpart_mass;
68
69 cgh.parallel_for(sycl::range<1>{pdat.get_obj_cnt()}, [=](sycl::item<1> item) {
70 u32 gid = (u32) item.get_id();
71 using namespace shamrock::sph;
72 Tscal rho_ha = rho_h(part_mass, acc_h[gid], Kernel::hfactd);
73 acc_rho[gid] = rho_ha;
74 });
75 });
76
77 buf_hpart.complete_event_state(e);
78 density.get_buf(p.id_patch).complete_event_state(e);
79 });
80
81 shamrock::LegacyVtkWriter writer = start_dump<Tvec>(scheduler(), filename);
82 writer.add_point_data_section();
83
84 u32 fnum = 0;
85 if (add_patch_world_id) {
86 fnum += 2;
87 }
88 fnum++;
89 fnum++;
90 fnum++;
91 fnum++;
92 fnum++;
93
94 if (solver_config.has_field_alphaAV()) {
95 fnum++;
96 }
97
98 if (solver_config.has_field_divv()) {
99 fnum++;
100 }
101
102 if (solver_config.has_field_curlv()) {
103 fnum++;
104 }
105
106 if (solver_config.has_field_soundspeed()) {
107 fnum++;
108 }
109
110 if (solver_config.has_field_dtdivv()) {
111 fnum++;
112 }
113
114 if (solver_config.compute_luminosity) {
115 fnum++;
116 }
117
118 if (solver_config.dust_config.has_epsilon_field()) {
119 const u32 ndust = solver_config.dust_config.get_dust_nvar();
120 fnum += ndust;
121 }
122
123 if (solver_config.dust_config.has_deltav_field()) {
124 const u32 ndust = solver_config.dust_config.get_dust_nvar();
125 fnum += ndust;
126 }
127
128 if (solver_config.dust_config.has_s_j_field()) {
129 const u32 ndust = solver_config.dust_config.get_dust_nvar();
130 fnum += ndust * 3; // s_j, ds_j_dt and delta_v
131 }
132
133 writer.add_field_data_section(fnum);
134
135 if (add_patch_world_id) {
136 vtk_dump_add_patch_id(scheduler(), writer);
137 vtk_dump_add_worldrank(scheduler(), writer);
138 }
139
140 vtk_dump_add_field<Tscal>(scheduler(), writer, ihpart, "h");
141 vtk_dump_add_field<Tscal>(scheduler(), writer, iuint, "u");
142 vtk_dump_add_field<Tvec>(scheduler(), writer, ivxyz, "v");
143 vtk_dump_add_field<Tvec>(scheduler(), writer, iaxyz, "a");
144
145 if (solver_config.has_field_alphaAV()) {
146 const u32 ialpha_AV = pdl.get_field_idx<Tscal>("alpha_AV");
147 vtk_dump_add_field<Tscal>(scheduler(), writer, ialpha_AV, "alpha_AV");
148 }
149
150 if (solver_config.has_field_divv()) {
151 const u32 idivv = pdl.get_field_idx<Tscal>("divv");
152 vtk_dump_add_field<Tscal>(scheduler(), writer, idivv, "divv");
153 }
154
155 if (solver_config.has_field_dtdivv()) {
156 const u32 idtdivv = pdl.get_field_idx<Tscal>("dtdivv");
157 vtk_dump_add_field<Tscal>(scheduler(), writer, idtdivv, "dtdivv");
158 }
159
160 if (solver_config.has_field_curlv()) {
161 const u32 icurlv = pdl.get_field_idx<Tvec>("curlv");
162 vtk_dump_add_field<Tvec>(scheduler(), writer, icurlv, "curlv");
163 }
164
165 if (solver_config.has_field_soundspeed()) {
166 const u32 isoundspeed = pdl.get_field_idx<Tscal>("soundspeed");
167 vtk_dump_add_field<Tscal>(scheduler(), writer, isoundspeed, "soundspeed");
168 }
169
170 if (solver_config.compute_luminosity) {
171 const u32 iluminosity = pdl.get_field_idx<Tscal>("luminosity");
172 vtk_dump_add_field<Tscal>(scheduler(), writer, iluminosity, "luminosity");
173 }
174
175 vtk_dump_add_compute_field(scheduler(), writer, density, "rho");
176
177 if (solver_config.dust_config.has_epsilon_field()) {
178 const u32 iepsilon = pdl.get_field_idx<Tscal>("epsilon");
179 const u32 ndust = solver_config.dust_config.get_dust_nvar();
180
181 for (u32 idust = 0; idust < ndust; idust++) {
182 ComputeField<Tscal> tmp_epsilon
183 = utility.make_compute_field<Tscal>("tmp_epsilon", 1);
184
185 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
186 shamlog_debug_ln(
187 "sph::vtk",
188 "compute extract epsilon field with idust =",
189 idust,
190 p.id_patch);
191
192 auto &buf_epsilon = pdat.get_field<Tscal>(iepsilon);
193 PatchDataFieldSpan<Tscal> span_epsilon{buf_epsilon, 0, pdat.get_obj_cnt()};
194
195 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
196 auto &q = sptr->get_queue();
197
199 q,
200 sham::MultiRef{span_epsilon},
201 sham::MultiRef{tmp_epsilon.get_buf(p.id_patch)},
202 pdat.get_obj_cnt(),
203 [&, idust](u32 i, auto epsilon_field, Tscal *acc_epsilon) {
204 acc_epsilon[i] = epsilon_field(i, idust);
205 });
206 });
207
209 scheduler(), writer, tmp_epsilon, "epsilon_" + std::to_string(idust));
210 }
211 }
212
213 if (solver_config.dust_config.has_deltav_field()) {
214 const u32 ideltav = pdl.get_field_idx<Tvec>("deltav");
215 const u32 ndust = solver_config.dust_config.get_dust_nvar();
216
217 for (u32 idust = 0; idust < ndust; idust++) {
218 ComputeField<Tvec> tmp_deltav = utility.make_compute_field<Tvec>("tmp_deltav", 1);
219
220 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
221 shamlog_debug_ln(
222 "sph::vtk", "compute extract deltav field with idust =", idust, p.id_patch);
223
224 auto &buf_deltav = pdat.get_field<Tvec>(ideltav);
225 PatchDataFieldSpan<Tvec> span_deltav{buf_deltav, 0, pdat.get_obj_cnt()};
226
227 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
228 auto &q = sptr->get_queue();
229
231 q,
232 sham::MultiRef{span_deltav},
233 sham::MultiRef{tmp_deltav.get_buf(p.id_patch)},
234 pdat.get_obj_cnt(),
235 [&, idust](u32 i, auto deltav_field, Tvec *acc_deltav) {
236 acc_deltav[i] = deltav_field(i, idust);
237 });
238 });
239
241 scheduler(), writer, tmp_deltav, "deltav_" + std::to_string(idust));
242 }
243 }
244
245 if (solver_config.dust_config.has_s_j_field()) {
246 const u32 is_j = pdl.get_field_idx<Tscal>("s_j");
247 const u32 ndust = solver_config.dust_config.get_dust_nvar();
248
249 for (u32 idust = 0; idust < ndust; idust++) {
250 ComputeField<Tscal> tmp_s_j = utility.make_compute_field<Tscal>("tmp_s_j", 1);
251
252 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
253 shamlog_debug_ln(
254 "sph::vtk", "compute extract s_j field with idust =", idust, p.id_patch);
255
256 auto &buf_s_j = pdat.get_field<Tscal>(is_j);
257 PatchDataFieldSpan<Tscal> span_s_j{buf_s_j, 0, pdat.get_obj_cnt()};
258
259 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
260 auto &q = sptr->get_queue();
261
263 q,
264 sham::MultiRef{span_s_j},
265 sham::MultiRef{tmp_s_j.get_buf(p.id_patch)},
266 pdat.get_obj_cnt(),
267 [&, idust](u32 i, auto s_j_field, Tscal *acc_s_j) {
268 acc_s_j[i] = s_j_field(i, idust);
269 });
270 });
271
273 scheduler(), writer, tmp_s_j, "s_j_" + std::to_string(idust));
274 }
275 }
276
277 if (solver_config.dust_config.has_s_j_field()) {
278 const u32 ids_j_dt = pdl.get_field_idx<Tscal>("ds_j_dt");
279 const u32 ndust = solver_config.dust_config.get_dust_nvar();
280
281 for (u32 idust = 0; idust < ndust; idust++) {
282 ComputeField<Tscal> tmp_ds_j_dt
283 = utility.make_compute_field<Tscal>("tmp_ds_j_dt", 1);
284
285 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
286 shamlog_debug_ln(
287 "sph::vtk",
288 "compute extract ds_j_dt field with idust =",
289 idust,
290 p.id_patch);
291
292 auto &buf_ds_j_dt = pdat.get_field<Tscal>(ids_j_dt);
293 PatchDataFieldSpan<Tscal> span_ds_j_dt{buf_ds_j_dt, 0, pdat.get_obj_cnt()};
294
295 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
296 auto &q = sptr->get_queue();
297
299 q,
300 sham::MultiRef{span_ds_j_dt},
301 sham::MultiRef{tmp_ds_j_dt.get_buf(p.id_patch)},
302 pdat.get_obj_cnt(),
303 [&, idust](u32 i, auto ds_j_dt_field, Tscal *acc_ds_j_dt) {
304 acc_ds_j_dt[i] = ds_j_dt_field(i, idust);
305 });
306 });
307
309 scheduler(), writer, tmp_ds_j_dt, "ds_j_dt_" + std::to_string(idust));
310 }
311 }
312
313 if (solver_config.dust_config.has_s_j_field()) {
314 const u32 idelta_v = pdl.get_field_idx<Tvec>("delta_v");
315 const u32 ndust = solver_config.dust_config.get_dust_nvar();
316
317 for (u32 idust = 0; idust < ndust; idust++) {
318 ComputeField<Tvec> tmp_delta_v = utility.make_compute_field<Tvec>("tmp_delta_v", 1);
319
320 scheduler().for_each_patchdata_nonempty([&](const Patch p, PatchDataLayer &pdat) {
321 shamlog_debug_ln(
322 "sph::vtk",
323 "compute extract delta_v field with idust =",
324 idust,
325 p.id_patch);
326
327 auto &buf_delta_v = pdat.get_field<Tvec>(idelta_v);
328 PatchDataFieldSpan<Tvec> span_delta_v{buf_delta_v, 0, pdat.get_obj_cnt()};
329
330 auto sptr = shamsys::instance::get_compute_scheduler_ptr();
331 auto &q = sptr->get_queue();
332
334 q,
335 sham::MultiRef{span_delta_v},
336 sham::MultiRef{tmp_delta_v.get_buf(p.id_patch)},
337 pdat.get_obj_cnt(),
338 [&, idust](u32 i, auto delta_v_field, Tvec *acc_delta_v) {
339 acc_delta_v[i] = delta_v_field(i, idust);
340 });
341 });
342
344 scheduler(), writer, tmp_delta_v, "delta_v_" + std::to_string(idust));
345 }
346 }
347 }
348
349} // namespace shammodels::sph::modules
350
351using namespace shammath;
352
356
Shared VTK dump utilities for SPH-based models.
void vtk_dump_add_compute_field(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer, shamrock::ComputeField< T > &field, const std::string &field_dump_name)
Add a compute field to VTK dump.
void vtk_dump_add_field(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer, u32 field_idx, const std::string &field_dump_name)
Add a data field to VTK dump.
shamrock::LegacyVtkWriter start_dump(PatchScheduler &sched, const std::string &dump_name)
Start a VTK dump by writing particle positions.
void vtk_dump_add_patch_id(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer)
Add patch ID field to VTK dump.
void vtk_dump_add_worldrank(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer)
Add world rank field to VTK dump.
std::uint32_t u32
32 bit unsigned integer
Class to manage a list of SYCL events.
Definition EventList.hpp:31
Module for writing VTK format output files.
Definition VTKDump.hpp:33
void do_dump(std::string filename, bool add_patch_world_id)
Writes particle data to VTK file for visualization.
Definition VTKDump.cpp:37
Represents a span of data within a PatchDataField.
ComputeField< T > make_compute_field(std::string new_name, u32 nvar)
create a compute field and init it to zeros
u32 get_field_idx(const std::string &field_name) const
Get the field id if matching name & type.
PatchDataLayer container class, the layout is described in patchdata_layout.
void kernel_call(sham::DeviceQueue &q, RefIn in, RefOut in_out, u32 n, Functor &&func, SourceLocation &&callsite=SourceLocation{})
Submit a kernel to a SYCL queue.
namespace for math utility
Definition AABB.hpp:26
namespace for the sph model modules
namespace for the main framework
Definition __init__.py:1
void vtk_dump_add_compute_field(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer, shamrock::ComputeField< T > &field, const std::string &field_dump_name)
Add a compute field to VTK dump.
void vtk_dump_add_field(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer, u32 field_idx, const std::string &field_dump_name)
Add a data field to VTK dump.
shamrock::LegacyVtkWriter start_dump(PatchScheduler &sched, const std::string &dump_name)
Start a VTK dump by writing particle positions.
void vtk_dump_add_patch_id(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer)
Add patch ID field to VTK dump.
void vtk_dump_add_worldrank(PatchScheduler &sched, shamrock::LegacyVtkWriter &writer)
Add world rank field to VTK dump.
shambase::details::BasicStackEntry StackEntry
Alias for shambase::details::BasicStackEntry.
A class that references multiple buffers or similar objects.
Definition MultiRef.hpp:33
Patch object that contain generic patch information.
Definition Patch.hpp:33