Skip to content

Commit 52554f9

Browse files
efaulhabersvchb
andauthored
Restructure TVF (#864)
* Restructure TVF * Remove dv term from newer paper * Eliminate time step from spatial discretization * Rename updates * Fix EDAC * Fix `current_density` * Fix sign of background pressure * Add reference * Implement suggestions * Remove `update_from_callback` * Implement suggestions * Fix tests * Fix background pressure factor * Improve comments * Fix boundary bug * Make N-Body system type-stable * Fix packing * Fix update callback * Update src/schemes/fluid/transport_velocity.jl Co-authored-by: Sven Berger <berger.sven@gmail.com> --------- Co-authored-by: Sven Berger <berger.sven@gmail.com>
1 parent dcfb854 commit 52554f9

24 files changed

Lines changed: 269 additions & 332 deletions

File tree

examples/n_body/n_body_system.jl

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
using TrixiParticles
22
using LinearAlgebra
33

4-
struct NBodySystem{NDIMS, ELTYPE <: Real} <: TrixiParticles.System{NDIMS}
5-
initial_condition :: InitialCondition{ELTYPE}
4+
struct NBodySystem{NDIMS, ELTYPE <: Real, IC} <: TrixiParticles.System{NDIMS}
5+
initial_condition :: IC
66
mass :: Array{ELTYPE, 1} # [particle]
77
G :: ELTYPE
88
buffer :: Nothing
@@ -11,13 +11,13 @@ struct NBodySystem{NDIMS, ELTYPE <: Real} <: TrixiParticles.System{NDIMS}
1111
mass = copy(initial_condition.mass)
1212

1313
new{size(initial_condition.coordinates, 1),
14-
eltype(mass)}(initial_condition, mass, G, nothing)
14+
eltype(mass), typeof(initial_condition)}(initial_condition, mass, G, nothing)
1515
end
1616
end
1717

1818
TrixiParticles.timer_name(::NBodySystem) = "nbody"
1919

20-
@inline Base.eltype(system::NBodySystem) = eltype(system.initial_condition.coordinates)
20+
@inline Base.eltype(system::NBodySystem{NDIMS, ELTYPE}) where {NDIMS, ELTYPE} = ELTYPE
2121

2222
function TrixiParticles.write_u0!(u0, system::NBodySystem)
2323
u0 .= system.initial_condition.coordinates

src/callbacks/density_reinit.jl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ function initialize_reinit_cb!(cb::DensityReinitializationCallback, u, t, integr
6969
# Update systems to compute quantities like density and pressure.
7070
semi = integrator.p
7171
v_ode, u_ode = u.x
72-
update_systems_and_nhs(v_ode, u_ode, semi, t; update_from_callback=true)
72+
update_systems_and_nhs(v_ode, u_ode, semi, t)
7373

7474
# Apply the callback.
7575
cb(integrator)

src/callbacks/particle_shifting.jl

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,7 @@ function particle_shifting!(integrator)
3939
# still have the values from the last stage of the previous step if not updated here.
4040
@trixi_timeit timer() "update systems and nhs" begin
4141
# Don't create sub-timers here to avoid cluttering the timer output
42-
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t;
43-
update_from_callback=true)
42+
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t)
4443
end
4544

4645
@trixi_timeit timer() "particle shifting" foreach_system(semi) do system

src/callbacks/post_process.jl

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -240,8 +240,7 @@ function (pp::PostprocessCallback)(integrator)
240240
# still have the values from the last stage of the previous step if not updated here.
241241
@trixi_timeit timer() "update systems and nhs" begin
242242
# Don't create sub-timers here to avoid cluttering the timer output
243-
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t;
244-
update_from_callback=true)
243+
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t)
245244
end
246245

247246
foreach_system(semi) do system

src/callbacks/update.jl

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ function initial_update!(cb::UpdateCallback, u, t, integrator)
5757

5858
# Tell systems that `UpdateCallback` is used
5959
foreach_system(semi) do system
60-
update_callback_used!(system)
60+
set_callback_flag!(system, true)
6161
end
6262

6363
return cb(integrator)
@@ -78,7 +78,7 @@ function (update_callback!::UpdateCallback)(integrator)
7878

7979
# Update quantities that are stored in the systems. These quantities (e.g. pressure)
8080
# still have the values from the last stage of the previous step if not updated here.
81-
update_systems_and_nhs(v_ode, u_ode, semi, t; update_from_callback=true)
81+
update_systems_and_nhs(v_ode, u_ode, semi, t)
8282

8383
# Update open boundaries first, since particles might be activated or deactivated
8484
@trixi_timeit timer() "update open boundary" foreach_system(semi) do system
@@ -89,6 +89,7 @@ function (update_callback!::UpdateCallback)(integrator)
8989
update_particle_packing(system, v_ode, u_ode, semi, integrator)
9090
end
9191

92+
# This is only used by the particle packing system and should be removed in the future
9293
@trixi_timeit timer() "update TVF" foreach_system(semi) do system
9394
update_transport_velocity!(system, v_ode, semi)
9495
end
@@ -141,5 +142,3 @@ function Base.show(io::IO, ::MIME"text/plain",
141142
summary_box(io, "UpdateCallback", setup)
142143
end
143144
end
144-
145-
update_callback_used!(system) = system

src/general/semidiscretization.jl

Lines changed: 44 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -338,8 +338,8 @@ function semidiscretize(semi, tspan; reset_threads=true)
338338
# Initialize this system
339339
initialize!(system, semi_new)
340340

341-
# Only for systems requiring a mandatory callback
342-
reset_callback_flag!(system)
341+
# Only for systems requiring the use of the `UpdateCallback`
342+
set_callback_flag!(system, false)
343343
end
344344

345345
return DynamicalODEProblem(kick!, drift!, v0_ode, u0_ode, tspan, semi_new)
@@ -373,8 +373,8 @@ function restart_with!(semi, sol; reset_threads=true)
373373

374374
restart_with!(system, v, u)
375375

376-
# Only for systems requiring a mandatory callback
377-
reset_callback_flag!(system)
376+
# Only for systems requiring the use of the `UpdateCallback`
377+
set_callback_flag!(system, false)
378378
end
379379

380380
return semi
@@ -464,17 +464,33 @@ function drift!(du_ode, v_ode, u_ode, semi, t)
464464
end
465465

466466
@inline function add_velocity!(du, v, particle, system)
467+
# Generic fallback for all systems that don't define this function
467468
for i in 1:ndims(system)
468-
du[i, particle] = v[i, particle]
469+
@inbounds du[i, particle] = v[i, particle]
469470
end
470471

471472
return du
472473
end
473474

475+
# Solid wall boundary system doesn't integrate the particle positions
474476
@inline add_velocity!(du, v, particle, system::BoundarySPHSystem) = du
475477

478+
@inline function add_velocity!(du, v, particle, system::FluidSystem)
479+
# This is zero unless a transport velocity is used
480+
delta_v_ = delta_v(system, particle)
481+
482+
for i in 1:ndims(system)
483+
@inbounds du[i, particle] = v[i, particle] + delta_v_[i]
484+
end
485+
486+
return du
487+
end
488+
476489
function kick!(dv_ode, v_ode, u_ode, semi, t)
477490
@trixi_timeit timer() "kick!" begin
491+
# Check that the `UpdateCallback` is used if required
492+
check_update_callback(semi)
493+
478494
@trixi_timeit timer() "reset ∂v/∂t" set_zero!(dv_ode)
479495

480496
@trixi_timeit timer() "update systems and nhs" update_systems_and_nhs(v_ode, u_ode,
@@ -490,8 +506,9 @@ function kick!(dv_ode, v_ode, u_ode, semi, t)
490506
return dv_ode
491507
end
492508

493-
# Update the systems and neighborhood searches (NHS) for a simulation before calling `interact!` to compute forces
494-
function update_systems_and_nhs(v_ode, u_ode, semi, t; update_from_callback=false)
509+
# Update the systems and neighborhood searches (NHS) for a simulation
510+
# before calling `interact!` to compute forces.
511+
function update_systems_and_nhs(v_ode, u_ode, semi, t)
495512
# First update step before updating the NHS
496513
# (for example for writing the current coordinates in the solid system)
497514
foreach_system(semi) do system
@@ -523,12 +540,21 @@ function update_systems_and_nhs(v_ode, u_ode, semi, t; update_from_callback=fals
523540
update_pressure!(system, v, u, v_ode, u_ode, semi, t)
524541
end
525542

543+
# This update depends on the computed quantities of the fluid system and therefore
544+
# needs to be after `update_quantities!`.
545+
foreach_system(semi) do system
546+
v = wrap_v(v_ode, system, semi)
547+
u = wrap_u(u_ode, system, semi)
548+
549+
update_boundary_interpolation!(system, v, u, v_ode, u_ode, semi, t)
550+
end
551+
526552
# Final update step for all remaining systems
527553
foreach_system(semi) do system
528554
v = wrap_v(v_ode, system, semi)
529555
u = wrap_u(u_ode, system, semi)
530556

531-
update_final!(system, v, u, v_ode, u_ode, semi, t; update_from_callback)
557+
update_final!(system, v, u, v_ode, u_ode, semi, t)
532558
end
533559
end
534560

@@ -858,6 +884,16 @@ function update!(neighborhood_search, x, y, semi; points_moving=(true, false),
858884
parallelization_backend=semi.parallelization_backend)
859885
end
860886

887+
function check_update_callback(semi)
888+
foreach_system(semi) do system
889+
# This check will be optimized away if the system does not require the callback
890+
if requires_update_callback(system) && !update_callback_used(system)
891+
system_name = system |> typeof |> nameof
892+
throw(ArgumentError("`UpdateCallback` is required for `$system_name`"))
893+
end
894+
end
895+
end
896+
861897
function check_configuration(systems,
862898
nhs::Union{Nothing, PointNeighbors.AbstractNeighborhoodSearch})
863899
foreach_system(systems) do system

src/general/system.jl

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ end
126126
system_correction(system), system, particle)
127127
end
128128

129-
# System update orders. This can be dispatched if needed.
129+
# System updates do nothing by default, but can be dispatched if needed
130130
function update_positions!(system, v, u, v_ode, u_ode, semi, t)
131131
return system
132132
end
@@ -139,21 +139,27 @@ function update_pressure!(system, v, u, v_ode, u_ode, semi, t)
139139
return system
140140
end
141141

142-
function update_final!(system, v, u, v_ode, u_ode, semi, t; update_from_callback=false)
142+
function update_boundary_interpolation!(system, v, u, v_ode, u_ode, semi, t)
143143
return system
144144
end
145145

146-
# Only for systems requiring a mandatory callback
147-
reset_callback_flag!(system) = system
146+
function update_final!(system, v, u, v_ode, u_ode, semi, t)
147+
return system
148+
end
149+
150+
# Only for systems requiring the use of the `UpdateCallback`
151+
@inline requires_update_callback(system) = false
152+
@inline update_callback_used(system) = false
153+
@inline set_callback_flag!(system, value) = system
148154

149-
initial_smoothing_length(system) = smoothing_length(system, nothing)
155+
@inline initial_smoothing_length(system) = smoothing_length(system, nothing)
150156

151-
function smoothing_length(system, particle)
157+
@inline function smoothing_length(system, particle)
152158
return system.smoothing_length
153159
end
154160

155-
system_smoothing_kernel(system) = system.smoothing_kernel
156-
system_correction(system) = nothing
161+
@inline system_smoothing_kernel(system) = system.smoothing_kernel
162+
@inline system_correction(system) = nothing
157163

158164
@inline particle_spacing(system, particle) = system.initial_condition.particle_spacing
159165

src/io/write_vtk.jl

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -58,8 +58,7 @@ function trixi2vtk(vu_ode, semi, t; iter=nothing, output_directory="out", prefix
5858
# still have the values from the last stage of the previous step if not updated here.
5959
@trixi_timeit timer() "update systems" begin
6060
# Don't create sub-timers here to avoid cluttering the timer output
61-
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t;
62-
update_from_callback=true)
61+
@notimeit timer() update_systems_and_nhs(v_ode, u_ode, semi, t)
6362
end
6463

6564
filenames = system_names(systems)

src/preprocessing/particle_packing/system.jl

Lines changed: 9 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -215,14 +215,15 @@ end
215215
return ndims(system)
216216
end
217217

218-
function reset_callback_flag!(system::ParticlePackingSystem)
219-
system.update_callback_used[] = false
218+
@inline requires_update_callback(system::ParticlePackingSystem) = true
219+
@inline update_callback_used(system::ParticlePackingSystem) = system.update_callback_used[]
220+
221+
function set_callback_flag!(system::ParticlePackingSystem, value)
222+
system.update_callback_used[] = value
220223

221224
return system
222225
end
223226

224-
update_callback_used!(system::ParticlePackingSystem) = system.update_callback_used[] = true
225-
226227
function write2vtk!(vtk, v, u, t, system::ParticlePackingSystem; write_meta_data=true)
227228
vtk["velocity"] = [advection_velocity(v, system, particle)
228229
for particle in active_particles(system)]
@@ -289,15 +290,6 @@ function update_position!(u, system::ParticlePackingSystem, semi)
289290
return u
290291
end
291292

292-
function update_final!(system::ParticlePackingSystem, v, u, v_ode, u_ode, semi, t;
293-
update_from_callback=false)
294-
if !update_from_callback && !(system.update_callback_used[])
295-
throw(ArgumentError("`UpdateCallback` is required when using `ParticlePackingSystem`"))
296-
end
297-
298-
return system
299-
end
300-
301293
# Skip for systems without `SignedDistanceField`
302294
constrain_particles_onto_surface!(u, system::ParticlePackingSystem{Nothing}, semi) = u
303295

@@ -398,6 +390,10 @@ end
398390
return system
399391
end
400392

393+
@inline function update_transport_velocity!(system, v_ode, semi)
394+
return system
395+
end
396+
401397
# Skip for fixed systems
402398
@inline add_velocity!(du, v, particle, system::ParticlePackingSystem{<:Any, true}) = du
403399

src/schemes/boundary/dummy_particles/dummy_particles.jl

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -311,17 +311,16 @@ end
311311
system, v, u, v_ode, u_ode, semi)
312312
(; correction, density_calculator) = boundary_model
313313

314-
compute_correction_values!(system, correction, u, v_ode, u_ode, semi)
314+
compute_pressure!(boundary_model, density_calculator, system, v, u, v_ode, u_ode, semi)
315315

316+
# These are only computed when using corrections
317+
compute_correction_values!(system, correction, u, v_ode, u_ode, semi)
316318
compute_gradient_correction_matrix!(correction, boundary_model, system, u, v_ode, u_ode,
317319
semi)
318-
319320
# `kernel_correct_density!` only performed for `SummationDensity`
320321
kernel_correct_density!(boundary_model, v, u, v_ode, u_ode, semi, correction,
321322
density_calculator)
322323

323-
compute_pressure!(boundary_model, density_calculator, system, v, u, v_ode, u_ode, semi)
324-
325324
return boundary_model
326325
end
327326

0 commit comments

Comments
 (0)