From 98dffee757dcf93f66c608bfd87bd8f38a151dbc Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 1 Jul 2021 22:18:10 -0500 Subject: [PATCH 01/58] implemented flux differencing volume kernel for SBP triangles --- .../elixir_euler_triangular_mesh_flux_diff.jl | 53 +++++++++++++ src/solvers/dg_simplices/dg.jl | 2 +- src/solvers/dg_simplices/fluxdiff.jl | 74 +++++++++++++++++++ 3 files changed, 128 insertions(+), 1 deletion(-) create mode 100644 examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl create mode 100644 src/solvers/dg_simplices/fluxdiff.jl diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl new file mode 100644 index 00000000000..0059e0abb33 --- /dev/null +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl @@ -0,0 +1,53 @@ +# !!! warning "Experimental features" + +using StartUpDG +using Trixi, OrdinaryDiffEq + +polydeg = 3 +rd = RefElemData(Tri(), SBP(), polydeg) + +volume_flux = flux_ranocha +dg = DG(rd, nothing #= mortar =#, + SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + +equations = CompressibleEulerEquations2D(1.4) +initial_condition = initial_condition_convergence_test +source_terms = source_terms_convergence_test + +# example where we tag two separate boundary segments of the mesh +top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) +VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 8) +mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) + +boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) +boundary_conditions = (; :top => boundary_condition_convergence_test, + :rest => boundary_condition_convergence_test) + +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms, + boundary_conditions = boundary_conditions) + +tspan = (0.0, .1) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +# u = ode.u0 +# du = similar(u) +# Trixi.rhs!(du, u, 0.0, mesh, equations, initial_condition, boundary_conditions, source_terms, dg, semi.cache) + +dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = .5*dt0, save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary + +l2,linf = analysis_callback(sol) diff --git a/src/solvers/dg_simplices/dg.jl b/src/solvers/dg_simplices/dg.jl index 093012d3f61..397a9bd9df1 100644 --- a/src/solvers/dg_simplices/dg.jl +++ b/src/solvers/dg_simplices/dg.jl @@ -81,7 +81,7 @@ function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, end function create_cache(mesh::VertexMappedMesh, equations, dg::DG, - RealT, uEltype) where {DG <: DGWeakForm{Dim}} where {Dim} + RealT, uEltype) where {DG <: Union{DGWeakForm{Dim}, SBPDGFluxDiff{Dim}}} where {Dim} rd = dg.basis md = mesh.md diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl new file mode 100644 index 00000000000..e449e0f41c4 --- /dev/null +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -0,0 +1,74 @@ +const DGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} +const PolyDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, Polynomial}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} +const SBPDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, <:SBP}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} + +""" + function hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) + +Computes the flux difference ∑_j Aij * f(u_i, u_j) and accumulates the result into `du`. +- `du`, `u` are vectors +- `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for +faster traversal since matrices are column major in Julia. +""" +function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} + for i in axes(ATr,2) + ui = u[i] + val_i = du[i] + for j in axes(ATr,1) + if skip_index(i,j) != true + val_i += ATr[j,i] * volume_flux(ui, u[j]) + end + end + du[i] = val_i + end +end + +function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, + mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} + + rd = dg.basis + @unpack local_values_threaded = cache + + volume_flux_oriented(i) = let i=i, equations=equations + (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) + end + + # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) + @threaded for e in eachelement(mesh, dg, cache) + u_local = view(u, :, e) + rhs_local = local_values_threaded[Threads.threadid()] + fill!(rhs_local, zero(eltype(rhs_local))) + for i in eachdim(mesh) + Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) + hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local) + end + view(du, :, e) .+= rhs_local ./ rd.wq + end +end + +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{2}, dg, cache) + @unpack Qrst_skew_Tr = cache + @unpack rxJ, sxJ, ryJ, syJ = mesh.md + QrskewTr, QsskewTr = Qrst_skew_Tr + if orientation == 1 + return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr)) + else + return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr)) + end +end + +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{3}, dg, cache) + @unpack Qrst_skew_Tr = cache + @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md + QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr + if orientation == 1 + return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr) + txJ[1,elem]*QtskewTr) + elseif orientation == 2 + return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr) + tyJ[1,elem]*QtskewTr) + else + return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr) + tzJ[1,elem]*QtskewTr) + end +end \ No newline at end of file From 18e0289bc9b39baf3c494695a4426086f02f0a0e Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 1 Jul 2021 23:06:41 -0500 Subject: [PATCH 02/58] renaming flux differencing elixir --- ...flux_diff.jl => elixir_euler_sbp_triangular_mesh_flux_diff.jl} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename examples/simplicial_2d_dg/{elixir_euler_triangular_mesh_flux_diff.jl => elixir_euler_sbp_triangular_mesh_flux_diff.jl} (100%) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl similarity index 100% rename from examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl rename to examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl From 8b0faa2d1f84d800c9475cfb665890296a720241 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 1 Jul 2021 23:07:00 -0500 Subject: [PATCH 03/58] removing StructArrays from elixirs --- examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl | 2 +- .../simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl | 2 +- examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl | 2 +- examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl | 2 +- .../elixir_euler_triangular_mesh_convergence.jl | 2 +- examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl | 2 +- 6 files changed, 6 insertions(+), 6 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl index b900810cadb..79abdf52154 100644 --- a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl @@ -1,6 +1,6 @@ # !!! warning "Experimental features" -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl index 562ea2efd22..9bb5479de42 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl @@ -1,6 +1,6 @@ # !!! warning "Experimental features" -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 diff --git a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl index 1ceac49bef5..a4e99193d15 100644 --- a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl @@ -1,6 +1,6 @@ # !!! warning "Experimental features" -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl index b7164a52dc7..b791b4e47c2 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl @@ -1,6 +1,6 @@ # !!! warning "Experimental features" -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl index 9b43286418c..2bea5c1403f 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl @@ -3,7 +3,7 @@ # run using # convergence_test(joinpath(examples_dir(), "triangular_mesh_2D", "elixir_euler_triangular_mesh_convergence.jl"), 4) -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 diff --git a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl index fda01a33e28..bb5e190df17 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl @@ -1,7 +1,7 @@ # !!! warning "Experimental features" using Triangulate -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 From cb6eaab76573c4d127cc65509efc22f3c177db5b Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 1 Jul 2021 23:07:20 -0500 Subject: [PATCH 04/58] factoring type aliases into separate file --- src/Trixi.jl | 1 + src/solvers/dg_simplices/dg.jl | 6 +----- src/solvers/dg_simplices/fluxdiff.jl | 7 ------- src/solvers/dg_simplices/type_aliases.jl | 10 ++++++++++ 4 files changed, 12 insertions(+), 12 deletions(-) create mode 100644 src/solvers/dg_simplices/type_aliases.jl diff --git a/src/Trixi.jl b/src/Trixi.jl index dd47591a594..ef8b00aeaaa 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -217,6 +217,7 @@ function __init__() include("solvers/dg_simplices/mesh.jl") export AbstractMeshData, VertexMappedMesh + include("solvers/dg_simplices/type_aliases.jl") include("solvers/dg_simplices/dg.jl") include("solvers/dg_simplices/fluxdiff.jl") include("solvers/dg_simplices/analysis.jl") diff --git a/src/solvers/dg_simplices/dg.jl b/src/solvers/dg_simplices/dg.jl index 397a9bd9df1..84074a4fbc0 100644 --- a/src/solvers/dg_simplices/dg.jl +++ b/src/solvers/dg_simplices/dg.jl @@ -23,10 +23,6 @@ mul_by_accum!(A, α) = let A = A @inline (out, x)->mul!(out, A, x, α, one(eltype(out))) end -const DGWeakForm{Dims, ElemType} = DG{<:RefElemData{Dims, ElemType}, Mortar, - <:SurfaceIntegralWeakForm, - <:VolumeIntegralWeakForm} where {Mortar} - # this is necessary for pretty printing Base.real(rd::RefElemData{Dims, Elem, ApproxType, Nfaces, RealT}) where {Dims, Elem, ApproxType, Nfaces, RealT} = RealT @@ -81,7 +77,7 @@ function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, end function create_cache(mesh::VertexMappedMesh, equations, dg::DG, - RealT, uEltype) where {DG <: Union{DGWeakForm{Dim}, SBPDGFluxDiff{Dim}}} where {Dim} + RealT, uEltype) where {DG <: Union{DGWeakForm, SBPDGFluxDiff}} rd = dg.basis md = mesh.md diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index e449e0f41c4..529e643ac98 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -1,10 +1,3 @@ -const DGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} -const PolyDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, Polynomial}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} -const SBPDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, <:SBP}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} - """ function hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) diff --git a/src/solvers/dg_simplices/type_aliases.jl b/src/solvers/dg_simplices/type_aliases.jl new file mode 100644 index 00000000000..ec9b8b445b5 --- /dev/null +++ b/src/solvers/dg_simplices/type_aliases.jl @@ -0,0 +1,10 @@ +const DGWeakForm{Dims, ElemType} = DG{<:RefElemData{Dims, ElemType}, Mortar, + <:SurfaceIntegralWeakForm, + <:VolumeIntegralWeakForm} where {Mortar} +const DGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} +const PolyDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, Polynomial}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} +const SBPDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, <:SBP}, + M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} + \ No newline at end of file From 32231953978d47d121b90f70757cc168f55a105c Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 2 Jul 2021 00:56:40 -0500 Subject: [PATCH 05/58] update type aliases more restrictive subtyping --- src/solvers/dg_simplices/type_aliases.jl | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/solvers/dg_simplices/type_aliases.jl b/src/solvers/dg_simplices/type_aliases.jl index ec9b8b445b5..53cc6eef75f 100644 --- a/src/solvers/dg_simplices/type_aliases.jl +++ b/src/solvers/dg_simplices/type_aliases.jl @@ -2,9 +2,9 @@ const DGWeakForm{Dims, ElemType} = DG{<:RefElemData{Dims, ElemType}, Mortar, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} where {Mortar} const DGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} + M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} const PolyDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, Polynomial}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} + M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} const SBPDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, <:SBP}, - M, S, <: VolumeIntegralFluxDifferencing} where {Dim, Elem, M, S} + M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} \ No newline at end of file From 2ecbda2b4e854b6b892ca7c75c78316f81664fb6 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 2 Jul 2021 00:57:17 -0500 Subject: [PATCH 06/58] implemented entropy stable flux differencing on triangular meshes tet meshes still have some bugs --- .../elixir_euler_triangular_mesh_flux_diff.jl | 49 ++++++ .../elixir_euler_tet_mesh_flux_diff.jl | 61 +++++++ src/solvers/dg_simplices/fluxdiff.jl | 150 +++++++++++++++--- 3 files changed, 241 insertions(+), 19 deletions(-) create mode 100644 examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl create mode 100644 examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl new file mode 100644 index 00000000000..d4e94a4e08c --- /dev/null +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl @@ -0,0 +1,49 @@ +# !!! warning "Experimental features" + +using StartUpDG +using Trixi, OrdinaryDiffEq + +polydeg = 3 +rd = RefElemData(Tri(), polydeg) + +volume_flux = flux_ranocha +dg = DG(rd, nothing #= mortar =#, + SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + +equations = CompressibleEulerEquations2D(1.4) +initial_condition = initial_condition_convergence_test +source_terms = source_terms_convergence_test + +# example where we tag two separate boundary segments of the mesh +top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) +VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 8) +mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) + +boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) +boundary_conditions = (; :top => boundary_condition_convergence_test, + :rest => boundary_condition_convergence_test) + +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms, + boundary_conditions = boundary_conditions) + +tspan = (0.0, .1) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = .5*dt0, save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary + +l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl new file mode 100644 index 00000000000..6f9587acb00 --- /dev/null +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl @@ -0,0 +1,61 @@ +# !!! warning "Experimental features" + +using StartUpDG +using Trixi, OrdinaryDiffEq + +polydeg = 3 +rd = RefElemData(Tet(), polydeg) + +volume_flux = flux_ranocha +dg = DG(rd, nothing #= mortar =#, + SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + +equations = CompressibleEulerEquations3D(1.4) +initial_condition = initial_condition_convergence_test +source_terms = source_terms_convergence_test + +IC_const(x,t,eq::CompressibleEulerEquations3D) = SVector{5}(2.,.1,.2,.3,2.5) +initial_condition = IC_const +source_terms = nothing + + +# example where we tag two separate boundary segments of the mesh +top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol +rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) +is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) +VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 4) +mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) + +boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) +boundary_conditions = (; :top => boundary_condition_convergence_test, + :rest => boundary_condition_convergence_test) + +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms, + boundary_conditions = boundary_conditions) + +tspan = (0.0, .1) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +u = ode.u0 +du = similar(u) +Trixi.rhs!(du, u, 0.0, mesh, equations, initial_condition, boundary_conditions, source_terms, dg, semi.cache) + +using LinearAlgebra: norm +norm(norm.(du)) + +# dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +# sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), +# dt = .5*dt0, save_everystep=false, callback=callbacks); +# summary_callback() # print the timer summary + +# l2,linf = analysis_callback(sol) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index 529e643ac98..a8eb752d4ce 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -19,6 +19,30 @@ function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) end end +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{2}, dg, cache) + @unpack Qrst_skew_Tr = cache + @unpack rxJ, sxJ, ryJ, syJ = mesh.md + QrskewTr, QsskewTr = Qrst_skew_Tr + if orientation == 1 + return LazyArray(@~ @. 2 * (rxJ[1,elem] * QrskewTr + sxJ[1,elem] * QsskewTr)) + else + return LazyArray(@~ @. 2 * (ryJ[1,elem] * QrskewTr + syJ[1,elem] * QsskewTr)) + end +end + +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{3}, dg, cache) + @unpack Qrst_skew_Tr = cache + @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md + QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr + if orientation == 1 + return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr) + txJ[1,elem]*QtskewTr) + elseif orientation == 2 + return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr) + tyJ[1,elem]*QtskewTr) + elseif orientation == 3 + return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr) + tzJ[1,elem]*QtskewTr) + end +end + function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} @@ -42,26 +66,114 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr end end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{2}, dg, cache) - @unpack Qrst_skew_Tr = cache - @unpack rxJ, sxJ, ryJ, syJ = mesh.md - QrskewTr, QsskewTr = Qrst_skew_Tr - if orientation == 1 - return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr)) - else - return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr)) + +function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, + RealT, uEltype) where {DG <: PolyDGFluxDiff} where {Dim} + + rd = dg.basis + @unpack md = mesh + + # Todo: simplices. Fix this when StartUpDG v0.11.0 releases + if Dim==2 + Qr_hybridized, Qs_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) + Qrst_hybridized = (Qr_hybridized, Qs_hybridized) + elseif Dim==3 + Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) + Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end + Qrst_skew_Tr = map(A->-.5*(A-A'), Qrst_hybridized) + # Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) + + nvars = nvariables(equations) + + # storage for all quadrature points (concatenated volume / face quadrature points) + num_quad_pts_total = rd.Nq + rd.Nfq + entropy_projected_u_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_pts_total, md.num_elements), nvars)) + projected_entropy_var_values = similar(entropy_projected_u_values) + + # initialize views into entropy_projected_u_values + u_values = view(entropy_projected_u_values, 1:rd.Nq, :) + u_face_values = view(entropy_projected_u_values, rd.Nq+1:num_quad_pts_total, :) + + # temp storage for entropy variables at volume quad points + entropy_var_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq, md.num_elements), nvars)) + + # local storage for interface fluxes, rhs, and source + flux_face_values = similar(u_face_values) + rhs_local_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_pts_total), nvars)) for _ in 1:Threads.nthreads()] + local_values_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq), nvars)) for _ in 1:Threads.nthreads()] + + return (; md, Qrst_skew_Tr, VhP, Ph, invJ = inv.(md.J), + entropy_var_values, projected_entropy_var_values, entropy_projected_u_values, + u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{3}, dg, cache) - @unpack Qrst_skew_Tr = cache - @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md - QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr - if orientation == 1 - return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr) + txJ[1,elem]*QtskewTr) - elseif orientation == 2 - return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr) + tyJ[1,elem]*QtskewTr) - else - return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr) + tzJ[1,elem]*QtskewTr) +function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, + equations, dg::DG) where {DG <: PolyDGFluxDiff} + + rd = dg.basis + @unpack Vq = rd + @unpack VhP, entropy_var_values, u_values, entropy_var_values = cache + @unpack projected_entropy_var_values, entropy_projected_u_values = cache + + # TODO: simplices. Address hard-coding of `entropy2cons!` + StructArrays.foreachfield(mul_by!(Vq), u_values, u) + entropy_var_values .= cons2entropy.(u_values, equations) + + # "VhP" fuses the projection "P" with interpolation to volume and face quadrature "Vh" + StructArrays.foreachfield(mul_by!(VhP), projected_entropy_var_values, entropy_var_values) + entropy_projected_u_values .= entropy2cons.(projected_entropy_var_values, equations) +end + +function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, + mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) + + rd = dg.basis + md = mesh.md + @unpack entropy_projected_u_values, rhs_local_threaded, Ph = cache + + volume_flux_oriented(i) = let i=i, equations=equations + (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) end -end \ No newline at end of file + + # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) + @threaded for e in eachelement(mesh, dg, cache) + u_local = view(entropy_projected_u_values, :, e) + rhs_local = rhs_local_threaded[Threads.threadid()] + fill!(rhs_local, zero(eltype(rhs_local))) + for i in eachdim(mesh) + Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) + hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, + (i,j)->i > rd.Nq && j > rd.Nq) + end + StructArrays.foreachfield(mul_by_accum!(Ph), view(du, :, e), rhs_local) + end +end + +function rhs!(du, u::StructArray, t, mesh, equations, + initial_condition, boundary_conditions::BC, source_terms::Source, + dg::PolyDGFluxDiff, cache) where {BC, Source} + + @trixi_timeit timer() "Reset du/dt" fill!(du,zero(eltype(du))) + + @trixi_timeit timer() "entropy_projection!" entropy_projection!(cache, u, mesh, equations, dg) + + @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, + mesh, equations, dg, cache) + + # the following functions are the same as in VolumeIntegralWeakForm, and can be reused from dg.jl + @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, mesh, equations, dg) + + @trixi_timeit timer() "calc_boundary_flux!" calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg) + + @trixi_timeit timer() "calc_surface_integral!" calc_surface_integral!(du, u, dg.surface_integral, mesh, equations, dg, cache) + + @trixi_timeit timer() "invert_jacobian" invert_jacobian!(du, mesh, equations, dg, cache) + + @trixi_timeit timer() "calc_sources!" calc_sources!(du, u, t, source_terms, mesh, equations, dg, cache) + + return nothing +end + + + From 6f16420eb1c58ff15716025ebb8ab64b5be55bab Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 2 Jul 2021 00:57:28 -0500 Subject: [PATCH 07/58] removing StructArrays from tet elixir --- examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl index 2cfc50aeafe..45731102644 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl @@ -1,6 +1,6 @@ # !!! warning "Experimental features" -using StartUpDG, StructArrays +using StartUpDG using Trixi, OrdinaryDiffEq polydeg = 3 From 9d7be5d4505ee50d9fa743a1cf9e5519410a3007 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 11:40:05 -0500 Subject: [PATCH 08/58] fixing bug in tet flux differencing --- .../elixir_euler_tet_mesh_flux_diff.jl | 24 +++++-------------- src/solvers/dg_simplices/fluxdiff.jl | 8 +++---- 2 files changed, 10 insertions(+), 22 deletions(-) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl index 6f9587acb00..6adf561780e 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl @@ -14,11 +14,6 @@ equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test -IC_const(x,t,eq::CompressibleEulerEquations3D) = SVector{5}(2.,.1,.2,.3,2.5) -initial_condition = IC_const -source_terms = nothing - - # example where we tag two separate boundary segments of the mesh top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) @@ -34,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, .1) +tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() @@ -46,16 +41,9 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -u = ode.u0 -du = similar(u) -Trixi.rhs!(du, u, 0.0, mesh, equations, initial_condition, boundary_conditions, source_terms, dg, semi.cache) - -using LinearAlgebra: norm -norm(norm.(du)) - -# dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) -# sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), -# dt = .5*dt0, save_everystep=false, callback=callbacks); -# summary_callback() # print the timer summary +dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = 0.5*dt0, save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary -# l2,linf = analysis_callback(sol) +l2,linf = analysis_callback(sol) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index a8eb752d4ce..6bbbeae8b75 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -32,14 +32,14 @@ end function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{3}, dg, cache) @unpack Qrst_skew_Tr = cache - @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr + @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md if orientation == 1 - return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr) + txJ[1,elem]*QtskewTr) + return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr + txJ[1,elem]*QtskewTr)) elseif orientation == 2 - return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr) + tyJ[1,elem]*QtskewTr) + return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr + tyJ[1,elem]*QtskewTr)) elseif orientation == 3 - return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr) + tzJ[1,elem]*QtskewTr) + return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr + tzJ[1,elem]*QtskewTr)) end end From bba3dd728b399f22779cc2e4c6ab78c2e63b33c7 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 11:40:30 -0500 Subject: [PATCH 09/58] clean up comments --- src/solvers/dg_simplices/fluxdiff.jl | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index 6bbbeae8b75..4475a6c0ccf 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -73,7 +73,7 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, rd = dg.basis @unpack md = mesh - # Todo: simplices. Fix this when StartUpDG v0.11.0 releases + # Todo: simplices. Fix this when StartUpDG v0.11.0 releases: new API `Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd)` if Dim==2 Qr_hybridized, Qs_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized) @@ -81,8 +81,8 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end - Qrst_skew_Tr = map(A->-.5*(A-A'), Qrst_hybridized) - # Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) + Qrst_skew_Tr = map(A -> -.5*(A-A'), Qrst_hybridized) + nvars = nvariables(equations) From 847d428528bb1803a364946dfd73bab825ebdc54 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 11:40:40 -0500 Subject: [PATCH 10/58] adding inlines and mul-adds --- src/solvers/dg_simplices/fluxdiff.jl | 29 +++++++++++++++------------- 1 file changed, 16 insertions(+), 13 deletions(-) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index 4475a6c0ccf..78b5476b3c5 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -6,16 +6,17 @@ Computes the flux difference ∑_j Aij * f(u_i, u_j) and accumulates the result - `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for faster traversal since matrices are column major in Julia. """ -function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} - for i in axes(ATr,2) +@inline @muladd function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} + rows,cols = axes(ATr) + for i in cols ui = u[i] val_i = du[i] - for j in axes(ATr,1) - if skip_index(i,j) != true - val_i += ATr[j,i] * volume_flux(ui, u[j]) + for j in rows + if !skip_index(i,j) + val_i += ATr[j,i] * volume_flux(ui, u[j]) end end - du[i] = val_i + du[i] = val_i end end @@ -50,14 +51,14 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr @unpack local_values_threaded = cache volume_flux_oriented(i) = let i=i, equations=equations - (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) + @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) end # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) @threaded for e in eachelement(mesh, dg, cache) - u_local = view(u, :, e) rhs_local = local_values_threaded[Threads.threadid()] fill!(rhs_local, zero(eltype(rhs_local))) + u_local = view(u, :, e) for i in eachdim(mesh) Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local) @@ -133,18 +134,20 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr @unpack entropy_projected_u_values, rhs_local_threaded, Ph = cache volume_flux_oriented(i) = let i=i, equations=equations - (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) + @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) end + # skips subblock of Qi_skew_Tr which we know is zero by construction + skip_index(i,j) = i > rd.Nq && j > rd.Nq + # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) @threaded for e in eachelement(mesh, dg, cache) - u_local = view(entropy_projected_u_values, :, e) rhs_local = rhs_local_threaded[Threads.threadid()] fill!(rhs_local, zero(eltype(rhs_local))) - for i in eachdim(mesh) + u_local = view(entropy_projected_u_values, :, e) + for i in eachdim(mesh) Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) - hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, - (i,j)->i > rd.Nq && j > rd.Nq) + hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, skip_index) end StructArrays.foreachfield(mul_by_accum!(Ph), view(du, :, e), rhs_local) end From 8b1d646571e8d59c58e6fc2c7c121f6086eae62c Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 11:47:33 -0500 Subject: [PATCH 11/58] changing tet mesh size in elixir (to satisfy 10 second test rule) --- .../simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl index 6adf561780e..26c515f7148 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl @@ -3,7 +3,7 @@ using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 +polydeg = 4 rd = RefElemData(Tet(), polydeg) volume_flux = flux_ranocha @@ -15,10 +15,10 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh -top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol +top_boundary(x, y, z, tol=50*eps()) = abs(z - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 4) +VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 2) mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) From 7454b4fc6009f4906d77f21e9cf40d0d51db79d3 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 15:05:10 -0500 Subject: [PATCH 12/58] adding `using Tet` from StartUpDG --- src/Trixi.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Trixi.jl b/src/Trixi.jl index ef8b00aeaaa..bc0fa4b831f 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -212,7 +212,7 @@ function __init__() # require StartUpDG for triangular mesh solvers @require StartUpDG="472ebc20-7c99-4d4b-9470-8fde4e9faa0f" begin using .StartUpDG: RefElemData, MeshData, Polynomial, SBP - using .StartUpDG: Line, Tri, Quad, Hex, AbstractElemShape + using .StartUpDG: Line, Tri, Tet, Quad, Hex, AbstractElemShape include("solvers/dg_simplices/mesh.jl") export AbstractMeshData, VertexMappedMesh From 5f452b9cf30cc6b7c41d8b03e0f6d5fe5ee85a42 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sat, 3 Jul 2021 15:07:09 -0500 Subject: [PATCH 13/58] specializing `build_lazy_physical_derivative` restricting to `VertexMappedMesh{NDIMS, <:Union{Tri, Tet}}`, which have constant geometric terms. Will specialize later to include affine quad/hex meshes. Todo: specialize for curved meshes. --- src/solvers/dg_simplices/fluxdiff.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index 78b5476b3c5..09e92e49e0a 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -20,7 +20,7 @@ faster traversal since matrices are column major in Julia. end end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{2}, dg, cache) +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::VertexMappedMesh{2, Tri}, dg, cache) @unpack Qrst_skew_Tr = cache @unpack rxJ, sxJ, ryJ, syJ = mesh.md QrskewTr, QsskewTr = Qrst_skew_Tr @@ -31,7 +31,7 @@ function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::Abstr end end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::AbstractMeshData{3}, dg, cache) +function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::VertexMappedMesh{3, Tet}, dg, cache) @unpack Qrst_skew_Tr = cache QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md From f38de4468e24e35f25a4bfc864f07094e9bcd0fb Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Sun, 4 Jul 2021 01:52:44 -0500 Subject: [PATCH 14/58] minor rearrangement of `using ...` and trimming whitespace --- src/Trixi.jl | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/Trixi.jl b/src/Trixi.jl index bc0fa4b831f..b76d410aa83 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -37,7 +37,7 @@ using LinearMaps: LinearMap using LoopVectorization: LoopVectorization, @turbo, indices using LoopVectorization.ArrayInterface: static_length import MPI -using Octavian: matmul! +using Octavian: matmul! using Polyester: @batch # You know, the cheapest threads you can find... using OffsetArrays: OffsetArray, OffsetVector using P4est @@ -212,15 +212,15 @@ function __init__() # require StartUpDG for triangular mesh solvers @require StartUpDG="472ebc20-7c99-4d4b-9470-8fde4e9faa0f" begin using .StartUpDG: RefElemData, MeshData, Polynomial, SBP - using .StartUpDG: Line, Tri, Tet, Quad, Hex, AbstractElemShape + using .StartUpDG: Line, Tri, Quad, Hex, Tet, AbstractElemShape include("solvers/dg_simplices/mesh.jl") export AbstractMeshData, VertexMappedMesh - + include("solvers/dg_simplices/type_aliases.jl") include("solvers/dg_simplices/dg.jl") include("solvers/dg_simplices/fluxdiff.jl") - include("solvers/dg_simplices/analysis.jl") + include("solvers/dg_simplices/analysis.jl") end end From 3c722ca3809ac3d8835b24f10a71084d03b37482 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 20:44:23 -0500 Subject: [PATCH 15/58] reducing number of elements in tests (make them slightly cheaper) --- .../simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl | 2 +- .../elixir_euler_periodic_triangular_mesh.jl | 2 +- .../elixir_euler_quadrilateral_mesh.jl | 2 +- .../elixir_euler_sbp_triangular_mesh_flux_diff.jl | 10 +++++----- .../simplicial_2d_dg/elixir_euler_triangular_mesh.jl | 2 +- .../elixir_euler_triangular_mesh_flux_diff.jl | 10 +++++----- .../elixir_euler_tet_mesh_flux_diff.jl | 10 +++++----- 7 files changed, 19 insertions(+), 19 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl index b5f04942c03..a26cc52c2da 100644 --- a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl @@ -16,7 +16,7 @@ equations = AcousticPerturbationEquations2D(v_mean_global, c_mean_global, rho_me initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 8) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd) # If no boundary tags are specified, VertexMappedMesh will add the tag `:entire_boundary` diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl index 718aa71f49a..c0fff2fab18 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl @@ -12,7 +12,7 @@ equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 8) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 4) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_periodic=(true,true)) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms) diff --git a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl index 9336be1f75b..2ed92206a1e 100644 --- a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl @@ -16,7 +16,7 @@ source_terms = source_terms_convergence_test top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 8) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 4) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl index 0059e0abb33..ee45b1b7457 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl @@ -7,7 +7,7 @@ polydeg = 3 rd = RefElemData(Tri(), SBP(), polydeg) volume_flux = flux_ranocha -dg = DG(rd, nothing #= mortar =#, +dg = DG(rd, nothing #= mortar =#, SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) equations = CompressibleEulerEquations2D(1.4) @@ -15,10 +15,10 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh -top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 8) +VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) @@ -26,8 +26,8 @@ boundary_conditions = (; :top => boundary_condition_convergence_test, :rest => boundary_condition_convergence_test) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) + source_terms = source_terms, + boundary_conditions = boundary_conditions) tspan = (0.0, .1) ode = semidiscretize(semi, tspan) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl index 35261a1f5fd..565268e518c 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl @@ -16,7 +16,7 @@ source_terms = source_terms_convergence_test top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 8) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl index d4e94a4e08c..2230d44b72c 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl @@ -7,7 +7,7 @@ polydeg = 3 rd = RefElemData(Tri(), polydeg) volume_flux = flux_ranocha -dg = DG(rd, nothing #= mortar =#, +dg = DG(rd, nothing #= mortar =#, SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) equations = CompressibleEulerEquations2D(1.4) @@ -15,10 +15,10 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh -top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 8) +VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) @@ -26,8 +26,8 @@ boundary_conditions = (; :top => boundary_condition_convergence_test, :rest => boundary_condition_convergence_test) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) + source_terms = source_terms, + boundary_conditions = boundary_conditions) tspan = (0.0, .1) ode = semidiscretize(semi, tspan) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl index 26c515f7148..1d5b6516c20 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl @@ -3,11 +3,11 @@ using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 4 +polydeg = 3 rd = RefElemData(Tet(), polydeg) volume_flux = flux_ranocha -dg = DG(rd, nothing #= mortar =#, +dg = DG(rd, nothing #= mortar =#, SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) equations = CompressibleEulerEquations3D(1.4) @@ -15,7 +15,7 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh -top_boundary(x, y, z, tol=50*eps()) = abs(z - 1) < tol +top_boundary(x, y, z, tol=50*eps()) = abs(z - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 2) @@ -26,8 +26,8 @@ boundary_conditions = (; :top => boundary_condition_convergence_test, :rest => boundary_condition_convergence_test) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) + source_terms = source_terms, + boundary_conditions = boundary_conditions) tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) From 201d8b72feef676626e6444fc44af7d4ea83cb03 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 20:44:33 -0500 Subject: [PATCH 16/58] adding simplicial flux differencing tests --- test/test_examples_2d_simplices.jl | 36 +++++++++++++++++++++--------- test/test_examples_3d_simplices.jl | 19 +++++++++++----- 2 files changed, 40 insertions(+), 15 deletions(-) diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_2d_simplices.jl index 98aba13ffb4..f42425571d7 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_2d_simplices.jl @@ -8,31 +8,31 @@ include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_2d_dg") -@testset "2D simplicial mesh tests" begin +@testset "2D simplicial mesh tests" begin @trixi_testset "elixir_euler_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh.jl"), - l2 = [7.687514677136661e-5, 8.844681835345058e-5, 8.844681835367038e-5, 0.0002667915678724591], - linf = [0.00023033713406972467, 0.0001967281286732181, 0.00019672812868742895, 0.0004570579510136952] + l2 = [0.0006456213233232335, 0.0012103605920880222, 0.0012103605920879606, 0.004127251610067376], + linf = [0.0007930980554167189, 0.0021736528649873854, 0.0021736528649864972, 0.005871873927952187] ) end @trixi_testset "elixir_euler_periodic_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_periodic_triangular_mesh.jl"), - l2 = [8.367502030645914e-5, 9.408647487246263e-5, 9.408647487253276e-5, 0.0002719897210980286], - linf = [0.00023033745877265588, 0.000196525001662895, 0.00019652500166067455, 0.000456252647166977] + l2 = [0.000672767625167618, 0.001269847226694384, 0.0012698472266944028, 0.004177337699476258], + linf = [0.0007498340156470995, 0.0021716152870556726, 0.002171615287057893, 0.005873584107397356] ) end @trixi_testset "elixir_ape_sbp_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_ape_sbp_triangular_mesh.jl"), - l2 = [0.025428732930900345, 0.02542873293089407, 0.01783409907430894, 0.0, 0.0, 0.0, 0.0], - linf = [0.04266081414305489, 0.04266081414679457, 0.03468583245492329, 0.0, 2.3455572625e-314, 2.3455070497e-314, 0.0] + l2 = [0.13498182674793963, 0.13498182674793793, 0.10409926243751662, 0.0, 0.0, 0.0, 0.0], + linf = [0.326623183281191, 0.3266231832808133, 0.349817130019491, 0.0, 0.0, 0.0, 0.0] ) end @trixi_testset "elixir_euler_triangulate_pkg_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangulate_pkg_mesh.jl"), - l2 = [0.0001016711916046445, 0.00011071422293274785, 0.00011212482087451142, 0.00035893791736543447], + l2 = [0.0001016711916046445, 0.00011071422293274785, 0.00011212482087451142, 0.00035893791736543447], linf = [0.00035073781634786805, 0.00039815763002271076, 0.00041642100745109545, 0.0009481311054404529] ) end @@ -47,8 +47,24 @@ end @testset "2D quadrilateral tests (using simplicial DG code)" begin @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), - l2 = [1.679658191261153e-5, 1.975052944338864e-5, 1.9750529443605503e-5, 6.243039564033164e-5], - linf = [4.21194288451332e-5, 4.386421462854173e-5, 4.386421466406887e-5, 9.206169546338572e-5] + l2 = [0.00015946119543800883, 0.000264475476940273, 0.00026447547694017894, 0.0008996889622631928], + linf = [0.0002365475762040603, 0.00032922335054608176, 0.0003292233505463038, 0.0012473538592372435] + ) + end +end + +@testset "2D simplicial flux differencing" begin + @trixi_testset "elixir_euler_triangular_mesh_flux_diff.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_flux_diff.jl"), + l2 = [0.0023756965829858814, 0.002810713803967761, 0.0028107138039682894, 0.008040750705578132], + linf = [0.004397202318891624, 0.00446064886127262, 0.004460648861263294, 0.012346721614063583] + ) + end + + @trixi_testset "elixir_euler_sbp_triangular_mesh_flux_diff.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_flux_diff.jl"), + l2 = [0.0019514080401385394, 0.00341875398076509, 0.0034187539807649155, 0.011829447744071755], + linf = [0.004078990424579931, 0.007257990068658904, 0.007257990068565867, 0.027380769039135444] ) end end diff --git a/test/test_examples_3d_simplices.jl b/test/test_examples_3d_simplices.jl index 9509cd3be57..6d7d5827382 100644 --- a/test/test_examples_3d_simplices.jl +++ b/test/test_examples_3d_simplices.jl @@ -8,15 +8,24 @@ include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_3d_dg") -@testset "3D simplicial mesh tests" begin - +@testset "3D simplicial mesh tests" begin @trixi_testset "elixir_euler_tet_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh.jl"), - l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], + l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] - ) + ) + end +end + +@testset "3D simplicial flux differencing tests" begin + + @trixi_testset "elixir_euler_tet_mesh_flux_diff.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh_flux_diff.jl"), + l2 = [0.04693516732847953, 0.0490148086446717, 0.048587225155397755, 0.04921946695784349, 0.12147656172990916], + linf = [0.10277064447821016, 0.12549628202719165, 0.11540362612261723, 0.12344556494598535, 0.3288299122603555] + ) end - + end end # module From 5fe19e1766d8d3b9d0096b2746977c391648c42e Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 21:29:48 -0500 Subject: [PATCH 17/58] renaming type_aliases.jl -> types_and_traits.jl - also updating PolyDGFluxDiff and SBPDGFluxDiff to use MultiDG type --- src/solvers/dg_simplices/type_aliases.jl | 16 ---------------- src/solvers/dg_simplices/types_and_traits.jl | 17 +++++++++++++++++ 2 files changed, 17 insertions(+), 16 deletions(-) delete mode 100644 src/solvers/dg_simplices/type_aliases.jl create mode 100644 src/solvers/dg_simplices/types_and_traits.jl diff --git a/src/solvers/dg_simplices/type_aliases.jl b/src/solvers/dg_simplices/type_aliases.jl deleted file mode 100644 index fa2e64d1d94..00000000000 --- a/src/solvers/dg_simplices/type_aliases.jl +++ /dev/null @@ -1,16 +0,0 @@ - -const MultiDG{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = - DG{<:RefElemData{NDIMS, ElemType, ApproxType}, Mortar, SurfaceIntegral, VolumeIntegral} where {Mortar} - -const MultiDGWeakForm{NDIMS, ElemType, ApproxType} = - MultiDG{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} - -# const DGWeakForm{Dims, ElemType} = DG{<:RefElemData{Dims, ElemType}, Mortar, -# <:SurfaceIntegralWeakForm, -# <:VolumeIntegralWeakForm} where {Mortar} -const DGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem}, - M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} -const PolyDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, Polynomial}, - M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} -const SBPDGFluxDiff{Dim, Elem} = DG{<:RefElemData{Dim, Elem, <:SBP}, - M, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {Dim, Elem, M} diff --git a/src/solvers/dg_simplices/types_and_traits.jl b/src/solvers/dg_simplices/types_and_traits.jl new file mode 100644 index 00000000000..9ce79fed28a --- /dev/null +++ b/src/solvers/dg_simplices/types_and_traits.jl @@ -0,0 +1,17 @@ + +# `MultiDG` refers to both multiple DG types (polynomial/SBP, simplices/quads/hexes) as well as +# the use of multi-dimensional operators in the solver. +const MultiDG{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = + DG{<:RefElemData{NDIMS, ElemType, ApproxType}, Mortar, SurfaceIntegral, VolumeIntegral} where {Mortar} + +const MultiDGWeakForm{NDIMS, ElemType, ApproxType} = + MultiDG{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} + +const PolyDGFluxDiff{NDIMS, ElemType} = + MultiDG{NDIMS, ElemType, Polynomial, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} + +const SBPDGFluxDiff{Dim, Elem} = + MultiDG{NDIMS, ElemType, <:SBP, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} + + +# Todo: simplices. Add traits for dispatch on affine/curved meshes here. \ No newline at end of file From 0c054042240048d871fdbb244696610c24e5aee3 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 22:14:48 -0500 Subject: [PATCH 18/58] adding flux diff elixirs to docs --- docs/src/meshes/mesh_data_meshes.md | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/docs/src/meshes/mesh_data_meshes.md b/docs/src/meshes/mesh_data_meshes.md index b2ced42a592..d3624b59599 100644 --- a/docs/src/meshes/mesh_data_meshes.md +++ b/docs/src/meshes/mesh_data_meshes.md @@ -123,3 +123,8 @@ Some key elixirs to look at: * `elixir_euler_triangulate_pkg_mesh.jl`: uses a `TriangulateIO` unstructured mesh generated by `Triangulate.jl`. * `elixir_ape_sbp_triangular_mesh.jl`: uses a multi-dimensional SBP discretization in weak form. * `elixir_euler_tet_mesh.jl`: basic weak form DG discretization on a uniform tet mesh. + +We also have support for flux differencing on simplicial meshes: +* `elixir_euler_triangular_mesh_flux_diff.jl`: Modal DG discretization with flux differencing on a uniform triangular mesh. +* `elixir_euler_sbp_triangular_mesh_flux_diff.jl`: SBP-DG discretization with flux differencing on a uniform triangular mesh. +* `elixir_euler_tet_mesh_flux_diff.jl`: Modal DG discretization with flux differencing on a uniform tetrahedral mesh. From cb16a26394c571108ba57adf1db36c8f6647eaee Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 22:16:11 -0500 Subject: [PATCH 19/58] renaming type_aliases.jl -> types_and_traits.jl in Trixi.jl --- src/Trixi.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Trixi.jl b/src/Trixi.jl index b76d410aa83..78fdc9801f7 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -217,7 +217,7 @@ function __init__() include("solvers/dg_simplices/mesh.jl") export AbstractMeshData, VertexMappedMesh - include("solvers/dg_simplices/type_aliases.jl") + include("solvers/dg_simplices/types_and_traits.jl") include("solvers/dg_simplices/dg.jl") include("solvers/dg_simplices/fluxdiff.jl") include("solvers/dg_simplices/analysis.jl") From fa1d6abfe2b47907e82d1bb3da19eb5bcff7f4ed Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 23:15:25 -0500 Subject: [PATCH 20/58] adding MultiDG convenience constructor --- src/solvers/dg_simplices/types_and_traits.jl | 27 ++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/src/solvers/dg_simplices/types_and_traits.jl b/src/solvers/dg_simplices/types_and_traits.jl index 9ce79fed28a..cd673c2ad1f 100644 --- a/src/solvers/dg_simplices/types_and_traits.jl +++ b/src/solvers/dg_simplices/types_and_traits.jl @@ -4,6 +4,33 @@ const MultiDG{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = DG{<:RefElemData{NDIMS, ElemType, ApproxType}, Mortar, SurfaceIntegral, VolumeIntegral} where {Mortar} +""" + MultiDG(; polydeg::Integer, + elem_type::AbstractElemShape, + approximation_type=Polynomial(), + surface_flux=flux_central, + surface_integral=SurfaceIntegralWeakForm(surface_flux), + volume_integral=VolumeIntegralWeakForm()) + +Create a discontinuous Galerkin method which uses +- approximations of polynomial degree `polydeg` +- element type `elem_type` (`Tri()`, `Quad()`, `Tet()`, and `Hex()` currently supported) + +Optional: +- approximation type of `approximation_type` (default is `Polynomial()`; `SBP()` also supported for +`Tri()`, `Quad()`, and `Hex()` element types). +""" +function MultiDG(; polydeg::Integer, + elem_type::AbstractElemShape, + approximation_type=Polynomial(), + surface_flux=flux_central, + surface_integral=SurfaceIntegralWeakForm(surface_flux), + volume_integral=VolumeIntegralWeakForm()) + rd = RefElemData(elem_type, approximation_type, polydeg) + return MultiDG(rd, surface_integral, volume_integral) +end + +# type aliases for dispatch purposes const MultiDGWeakForm{NDIMS, ElemType, ApproxType} = MultiDG{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} From 5cc9542967a7a31468abce4d7d6d9d33b77c3190 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 23:57:56 -0500 Subject: [PATCH 21/58] Apply suggestions from code review Co-authored-by: Hendrik Ranocha --- ...xir_euler_sbp_triangular_mesh_flux_diff.jl | 6 ++-- .../elixir_euler_triangular_mesh_flux_diff.jl | 4 +-- src/solvers/dg_simplices/fluxdiff.jl | 29 +++++++++---------- 3 files changed, 18 insertions(+), 21 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl index ee45b1b7457..78471513c42 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, .1) +tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() @@ -47,7 +47,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = .5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl index 2230d44b72c..6abb33f58ab 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, .1) +tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() @@ -43,7 +43,7 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = .5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary l2,linf = analysis_callback(sol) diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_simplices/fluxdiff.jl index 09e92e49e0a..3e5579c76da 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_simplices/fluxdiff.jl @@ -1,26 +1,26 @@ """ - function hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) + hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) -Computes the flux difference ∑_j Aij * f(u_i, u_j) and accumulates the result into `du`. +Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the result into `du`. - `du`, `u` are vectors - `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for -faster traversal since matrices are column major in Julia. + faster traversal since matrices are column major in Julia. """ -@inline @muladd function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} - rows,cols = axes(ATr) +@inline function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} + rows, cols = axes(ATr) for i in cols - ui = u[i] - val_i = du[i] + u_i = u[i] + du_i = du[i] for j in rows if !skip_index(i,j) - val_i += ATr[j,i] * volume_flux(ui, u[j]) + du_i += ATr[j,i] * volume_flux(u_i, u[j]) end end - du[i] = val_i + du[i] = du_i end end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::VertexMappedMesh{2, Tri}, dg, cache) +function build_lazy_physical_derivative(element::Int, orientation::Int, mesh::VertexMappedMesh{2, Tri}, dg, cache) @unpack Qrst_skew_Tr = cache @unpack rxJ, sxJ, ryJ, syJ = mesh.md QrskewTr, QsskewTr = Qrst_skew_Tr @@ -45,7 +45,7 @@ function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::Verte end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, - mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} + mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} rd = dg.basis @unpack local_values_threaded = cache @@ -75,10 +75,10 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, @unpack md = mesh # Todo: simplices. Fix this when StartUpDG v0.11.0 releases: new API `Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd)` - if Dim==2 + if Dim == 2 Qr_hybridized, Qs_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized) - elseif Dim==3 + elseif Dim == 3 Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end @@ -127,7 +127,7 @@ function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, - mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) + mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) rd = dg.basis md = mesh.md @@ -179,4 +179,3 @@ function rhs!(du, u::StructArray, t, mesh, equations, end - From 07e94bce44ac6827f3a07f9d039757f88ba6da4d Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 5 Jul 2021 23:58:48 -0500 Subject: [PATCH 22/58] Update examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl Co-authored-by: Hendrik Ranocha --- .../elixir_euler_sbp_triangular_mesh_flux_diff.jl | 4 ---- 1 file changed, 4 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl index 78471513c42..c655f456539 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl @@ -41,10 +41,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -# u = ode.u0 -# du = similar(u) -# Trixi.rhs!(du, u, 0.0, mesh, equations, initial_condition, boundary_conditions, source_terms, dg, semi.cache) - dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); From 2d5ad64270c9c4a0ddfc636dfa427bc0c397a310 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 6 Jul 2021 21:48:29 -0600 Subject: [PATCH 23/58] renaming folder to `dg_multi` --- src/Trixi.jl | 12 +-- .../{dg_simplices => dg_multi}/analysis.jl | 0 src/solvers/{dg_simplices => dg_multi}/dg.jl | 0 .../{dg_simplices => dg_multi}/fluxdiff.jl | 81 ++++++++++--------- .../{dg_simplices => dg_multi}/mesh.jl | 0 .../types_and_traits.jl | 2 +- 6 files changed, 49 insertions(+), 46 deletions(-) rename src/solvers/{dg_simplices => dg_multi}/analysis.jl (100%) rename src/solvers/{dg_simplices => dg_multi}/dg.jl (100%) rename src/solvers/{dg_simplices => dg_multi}/fluxdiff.jl (74%) rename src/solvers/{dg_simplices => dg_multi}/mesh.jl (100%) rename src/solvers/{dg_simplices => dg_multi}/types_and_traits.jl (96%) diff --git a/src/Trixi.jl b/src/Trixi.jl index 78fdc9801f7..20af49ec14b 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -214,13 +214,15 @@ function __init__() using .StartUpDG: RefElemData, MeshData, Polynomial, SBP using .StartUpDG: Line, Tri, Quad, Hex, Tet, AbstractElemShape - include("solvers/dg_simplices/mesh.jl") + include("solvers/dg_multi/mesh.jl") export AbstractMeshData, VertexMappedMesh - include("solvers/dg_simplices/types_and_traits.jl") - include("solvers/dg_simplices/dg.jl") - include("solvers/dg_simplices/fluxdiff.jl") - include("solvers/dg_simplices/analysis.jl") + include("solvers/dg_multi/types_and_traits.jl") + export MultiDG + + include("solvers/dg_multi/dg.jl") + include("solvers/dg_multi/fluxdiff.jl") + include("solvers/dg_multi/analysis.jl") end end diff --git a/src/solvers/dg_simplices/analysis.jl b/src/solvers/dg_multi/analysis.jl similarity index 100% rename from src/solvers/dg_simplices/analysis.jl rename to src/solvers/dg_multi/analysis.jl diff --git a/src/solvers/dg_simplices/dg.jl b/src/solvers/dg_multi/dg.jl similarity index 100% rename from src/solvers/dg_simplices/dg.jl rename to src/solvers/dg_multi/dg.jl diff --git a/src/solvers/dg_simplices/fluxdiff.jl b/src/solvers/dg_multi/fluxdiff.jl similarity index 74% rename from src/solvers/dg_simplices/fluxdiff.jl rename to src/solvers/dg_multi/fluxdiff.jl index 3e5579c76da..06ce9697614 100644 --- a/src/solvers/dg_simplices/fluxdiff.jl +++ b/src/solvers/dg_multi/fluxdiff.jl @@ -1,10 +1,10 @@ """ hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) -Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the result into `du`. +Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the result into `du`. - `du`, `u` are vectors -- `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for - faster traversal since matrices are column major in Julia. +- `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for + faster traversal since matrices are column major in Julia. """ @inline function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} rows, cols = axes(ATr) @@ -12,54 +12,58 @@ Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the res u_i = u[i] du_i = du[i] for j in rows - if !skip_index(i,j) + if !skip_index(i,j) du_i += ATr[j,i] * volume_flux(u_i, u[j]) end end - du[i] = du_i + du[i] = du_i end end -function build_lazy_physical_derivative(element::Int, orientation::Int, mesh::VertexMappedMesh{2, Tri}, dg, cache) +# For MultiDG implementations, we construct "physical" differentiation operators by taking linear +# combinations of reference differentiation operators scaled by geometric change of variables terms. +# We use LazyArrays.jl for lazy evaluation of physical differentiation operators, so that we can +# compute linear combinations of differentiation operators on-the-fly in an allocation-free manner. +function build_lazy_physical_derivative(element::Int, orientation::Int, + mesh::VertexMappedMesh{2, Tri}, dg, cache) @unpack Qrst_skew_Tr = cache @unpack rxJ, sxJ, ryJ, syJ = mesh.md QrskewTr, QsskewTr = Qrst_skew_Tr if orientation == 1 - return LazyArray(@~ @. 2 * (rxJ[1,elem] * QrskewTr + sxJ[1,elem] * QsskewTr)) + return LazyArray(@~ @. 2 * (rxJ[1,element] * QrskewTr + sxJ[1,element] * QsskewTr)) else - return LazyArray(@~ @. 2 * (ryJ[1,elem] * QrskewTr + syJ[1,elem] * QsskewTr)) + return LazyArray(@~ @. 2 * (ryJ[1,element] * QrskewTr + syJ[1,element] * QsskewTr)) end end -function build_lazy_physical_derivative(elem::Int, orientation::Int, mesh::VertexMappedMesh{3, Tet}, dg, cache) +function build_lazy_physical_derivative(element::Int, orientation::Int, + mesh::VertexMappedMesh{3, Tet}, dg, cache) @unpack Qrst_skew_Tr = cache QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr @unpack rxJ, sxJ, txJ, ryJ, syJ, tyJ, rzJ, szJ, tzJ = mesh.md if orientation == 1 - return LazyArray(@~ @. 2 * (rxJ[1,elem]*QrskewTr + sxJ[1,elem]*QsskewTr + txJ[1,elem]*QtskewTr)) + return LazyArray(@~ @. 2 * (rxJ[1,element]*QrskewTr + sxJ[1,element]*QsskewTr + txJ[1,element]*QtskewTr)) elseif orientation == 2 - return LazyArray(@~ @. 2 * (ryJ[1,elem]*QrskewTr + syJ[1,elem]*QsskewTr + tyJ[1,elem]*QtskewTr)) + return LazyArray(@~ @. 2 * (ryJ[1,element]*QrskewTr + syJ[1,element]*QsskewTr + tyJ[1,element]*QtskewTr)) elseif orientation == 3 - return LazyArray(@~ @. 2 * (rzJ[1,elem]*QrskewTr + szJ[1,elem]*QsskewTr + tzJ[1,elem]*QtskewTr)) + return LazyArray(@~ @. 2 * (rzJ[1,element]*QrskewTr + szJ[1,element]*QsskewTr + tzJ[1,element]*QtskewTr)) end end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} - rd = dg.basis + rd = dg.basis @unpack local_values_threaded = cache - volume_flux_oriented(i) = let i=i, equations=equations - @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) - end + volume_flux_oriented(i) = @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) @threaded for e in eachelement(mesh, dg, cache) rhs_local = local_values_threaded[Threads.threadid()] fill!(rhs_local, zero(eltype(rhs_local))) u_local = view(u, :, e) - for i in eachdim(mesh) + for i in eachdim(mesh) Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local) end @@ -68,19 +72,19 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr end -function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, +function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, RealT, uEltype) where {DG <: PolyDGFluxDiff} where {Dim} rd = dg.basis @unpack md = mesh - + # Todo: simplices. Fix this when StartUpDG v0.11.0 releases: new API `Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd)` if Dim == 2 Qr_hybridized, Qs_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) - Qrst_hybridized = (Qr_hybridized, Qs_hybridized) + Qrst_hybridized = (Qr_hybridized, Qs_hybridized) elseif Dim == 3 Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) - Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) + Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end Qrst_skew_Tr = map(A -> -.5*(A-A'), Qrst_hybridized) @@ -88,28 +92,28 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, nvars = nvariables(equations) # storage for all quadrature points (concatenated volume / face quadrature points) - num_quad_pts_total = rd.Nq + rd.Nfq - entropy_projected_u_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_pts_total, md.num_elements), nvars)) + num_quad_points_total = rd.Nq + rd.Nfq + entropy_projected_u_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_points_total, md.num_elements), nvars)) projected_entropy_var_values = similar(entropy_projected_u_values) # initialize views into entropy_projected_u_values u_values = view(entropy_projected_u_values, 1:rd.Nq, :) - u_face_values = view(entropy_projected_u_values, rd.Nq+1:num_quad_pts_total, :) + u_face_values = view(entropy_projected_u_values, rd.Nq+1:num_quad_points_total, :) # temp storage for entropy variables at volume quad points entropy_var_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq, md.num_elements), nvars)) # local storage for interface fluxes, rhs, and source flux_face_values = similar(u_face_values) - rhs_local_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_pts_total), nvars)) for _ in 1:Threads.nthreads()] + rhs_local_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(num_quad_points_total), nvars)) for _ in 1:Threads.nthreads()] local_values_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq), nvars)) for _ in 1:Threads.nthreads()] - - return (; md, Qrst_skew_Tr, VhP, Ph, invJ = inv.(md.J), + + return (; md, Qrst_skew_Tr, VhP, Ph, invJ = inv.(md.J), entropy_var_values, projected_entropy_var_values, entropy_projected_u_values, u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end -function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, +function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, equations, dg::DG) where {DG <: PolyDGFluxDiff} rd = dg.basis @@ -121,21 +125,18 @@ function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, StructArrays.foreachfield(mul_by!(Vq), u_values, u) entropy_var_values .= cons2entropy.(u_values, equations) - # "VhP" fuses the projection "P" with interpolation to volume and face quadrature "Vh" + # "VhP" fuses the projection "P" with interpolation to volume and face quadrature "Vh" StructArrays.foreachfield(mul_by!(VhP), projected_entropy_var_values, entropy_var_values) entropy_projected_u_values .= entropy2cons.(projected_entropy_var_values, equations) end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, - mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) + mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) - rd = dg.basis + rd = dg.basis md = mesh.md @unpack entropy_projected_u_values, rhs_local_threaded, Ph = cache - - volume_flux_oriented(i) = let i=i, equations=equations - @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) - end + volume_flux_oriented(i) = @inline (u_ll, u_rr)->volume_integral.volume_flux(u_ll, u_rr, i, equations) # skips subblock of Qi_skew_Tr which we know is zero by construction skip_index(i,j) = i > rd.Nq && j > rd.Nq @@ -150,10 +151,10 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, skip_index) end StructArrays.foreachfield(mul_by_accum!(Ph), view(du, :, e), rhs_local) - end + end end -function rhs!(du, u::StructArray, t, mesh, equations, +function rhs!(du, u::StructArray, t, mesh, equations, initial_condition, boundary_conditions::BC, source_terms::Source, dg::PolyDGFluxDiff, cache) where {BC, Source} @@ -161,16 +162,16 @@ function rhs!(du, u::StructArray, t, mesh, equations, @trixi_timeit timer() "entropy_projection!" entropy_projection!(cache, u, mesh, equations, dg) - @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, + @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, mesh, equations, dg, cache) - # the following functions are the same as in VolumeIntegralWeakForm, and can be reused from dg.jl + # the following functions are the same as in VolumeIntegralWeakForm, and can be reused from dg.jl @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, mesh, equations, dg) @trixi_timeit timer() "calc_boundary_flux!" calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg) @trixi_timeit timer() "calc_surface_integral!" calc_surface_integral!(du, u, dg.surface_integral, mesh, equations, dg, cache) - + @trixi_timeit timer() "invert_jacobian" invert_jacobian!(du, mesh, equations, dg, cache) @trixi_timeit timer() "calc_sources!" calc_sources!(du, u, t, source_terms, mesh, equations, dg, cache) diff --git a/src/solvers/dg_simplices/mesh.jl b/src/solvers/dg_multi/mesh.jl similarity index 100% rename from src/solvers/dg_simplices/mesh.jl rename to src/solvers/dg_multi/mesh.jl diff --git a/src/solvers/dg_simplices/types_and_traits.jl b/src/solvers/dg_multi/types_and_traits.jl similarity index 96% rename from src/solvers/dg_simplices/types_and_traits.jl rename to src/solvers/dg_multi/types_and_traits.jl index cd673c2ad1f..c75a8b196f2 100644 --- a/src/solvers/dg_simplices/types_and_traits.jl +++ b/src/solvers/dg_multi/types_and_traits.jl @@ -27,7 +27,7 @@ function MultiDG(; polydeg::Integer, surface_integral=SurfaceIntegralWeakForm(surface_flux), volume_integral=VolumeIntegralWeakForm()) rd = RefElemData(elem_type, approximation_type, polydeg) - return MultiDG(rd, surface_integral, volume_integral) + return DG(rd, nothing #= mortar =#, surface_integral, volume_integral) end # type aliases for dispatch purposes From d5808dd1ef57c0f88108bd57ca45eba2cf18983f Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 6 Jul 2021 22:20:53 -0600 Subject: [PATCH 24/58] removing extra l2, linf error printouts --- .../simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl | 2 -- .../elixir_euler_periodic_triangular_mesh.jl | 2 -- .../simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl | 2 -- examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl | 2 -- .../elixir_euler_triangular_mesh_convergence.jl | 2 -- ...sh_flux_diff.jl => elixir_euler_triangular_mesh_ec.jl} | 8 +++----- .../simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl | 8 +++----- examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl | 6 ++---- ..._tet_mesh_flux_diff.jl => elixir_euler_tet_mesh_ec.jl} | 8 +++----- 9 files changed, 11 insertions(+), 29 deletions(-) rename examples/simplicial_2d_dg/{elixir_euler_triangular_mesh_flux_diff.jl => elixir_euler_triangular_mesh_ec.jl} (90%) rename examples/simplicial_3d_dg/{elixir_euler_tet_mesh_flux_diff.jl => elixir_euler_tet_mesh_ec.jl} (91%) diff --git a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl index a26cc52c2da..7c4f3785fe0 100644 --- a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl @@ -43,5 +43,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = .5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl index c0fff2fab18..10b29282681 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl @@ -33,5 +33,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl index 2ed92206a1e..91342121a75 100644 --- a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl @@ -43,5 +43,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl index 565268e518c..5e277204353 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl @@ -43,5 +43,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl index 9e9779aec72..9ebd780fc8a 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl @@ -43,5 +43,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl similarity index 90% rename from examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl rename to examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl index 6abb33f58ab..d702c004951 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl @@ -6,9 +6,9 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tri(), polydeg) -volume_flux = flux_ranocha dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + SurfaceIntegralWeakForm(FluxLaxFriedrichs()), + VolumeIntegralFluxDifferencing(flux_ranocha)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.4) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() @@ -45,5 +45,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl index 1b6cc9c1c16..c7845762fa0 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl @@ -15,7 +15,7 @@ source_terms = source_terms_convergence_test meshIO = StartUpDG.square_hole_domain(.25) # pre-defined Triangulate geometry in StartUpDG -# the pre-defined Triangulate geometry in StartUpDG has integer boundary tags. this routine +# the pre-defined Triangulate geometry in StartUpDG has integer boundary tags. this routine # assigns boundary faces based on these integer boundary tags. mesh = VertexMappedMesh(meshIO, rd, Dict(:bottom=>1, :right=>2, :top=>3, :left=>4)) @@ -26,8 +26,8 @@ boundary_conditions = (; :bottom => boundary_condition_convergence_test, :left => boundary_condition_convergence_test) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) + source_terms = source_terms, + boundary_conditions = boundary_conditions) tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) @@ -45,5 +45,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl index 60648948474..1c65b4adfcd 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl @@ -24,8 +24,8 @@ boundary_conditions = (; :top => boundary_condition_convergence_test, :rest => boundary_condition_convergence_test) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) + source_terms = source_terms, + boundary_conditions = boundary_conditions) tspan = (0.0, 0.1) ode = semidiscretize(semi, tspan) @@ -43,5 +43,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl similarity index 91% rename from examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl rename to examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl index 1d5b6516c20..55241a5fe7e 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_flux_diff.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl @@ -6,9 +6,9 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tet(), polydeg) -volume_flux = flux_ranocha dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + SurfaceIntegralWeakForm(FluxLaxFriedrichs()), + VolumeIntegralFluxDifferencing(flux_ranocha)) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.25) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() @@ -45,5 +45,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -l2,linf = analysis_callback(sol) From b321371a229e7120d1e40dc3daa558a24bcaf838 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 6 Jul 2021 22:21:24 -0600 Subject: [PATCH 25/58] fixing names of elixirs in docs --- docs/src/meshes/mesh_data_meshes.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/src/meshes/mesh_data_meshes.md b/docs/src/meshes/mesh_data_meshes.md index d3624b59599..1dc78fd1881 100644 --- a/docs/src/meshes/mesh_data_meshes.md +++ b/docs/src/meshes/mesh_data_meshes.md @@ -125,6 +125,6 @@ Some key elixirs to look at: * `elixir_euler_tet_mesh.jl`: basic weak form DG discretization on a uniform tet mesh. We also have support for flux differencing on simplicial meshes: -* `elixir_euler_triangular_mesh_flux_diff.jl`: Modal DG discretization with flux differencing on a uniform triangular mesh. -* `elixir_euler_sbp_triangular_mesh_flux_diff.jl`: SBP-DG discretization with flux differencing on a uniform triangular mesh. -* `elixir_euler_tet_mesh_flux_diff.jl`: Modal DG discretization with flux differencing on a uniform tetrahedral mesh. +* `elixir_euler_triangular_mesh_ec.jl`: Modal DG discretization with flux differencing on a uniform triangular mesh. +* `elixir_euler_sbp_triangular_mesh_ec.jl`: SBP-DG discretization with flux differencing on a uniform triangular mesh. +* `elixir_euler_tet_mesh_ec.jl`: Modal DG discretization with flux differencing on a uniform tetrahedral mesh. From 50464d35a4be786f4ed78e9d421f3fc088a0fe40 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Wed, 7 Jul 2021 21:31:41 -0700 Subject: [PATCH 26/58] trim whitespace --- examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl index 1c65b4adfcd..08f77b8d708 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl @@ -5,7 +5,7 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tet(), polydeg) -dg = DG(rd, nothing #= mortar =#, +dg = DG(rd, nothing #= mortar =#, SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) equations = CompressibleEulerEquations3D(1.4) @@ -13,7 +13,7 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh -top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol +top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 4) From ed5cb958400e8f737354e58925f36cc6b7ba282a Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Wed, 7 Jul 2021 22:17:58 -0700 Subject: [PATCH 27/58] renaming flux_diff -> ec --- ...lixir_euler_periodic_triangular_mesh_ec.jl | 44 +++++++++++++++++++ ...=> elixir_euler_sbp_triangular_mesh_ec.jl} | 2 +- test/test_examples_2d_simplices.jl | 8 ++-- 3 files changed, 49 insertions(+), 5 deletions(-) create mode 100644 examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl rename examples/simplicial_2d_dg/{elixir_euler_sbp_triangular_mesh_flux_diff.jl => elixir_euler_sbp_triangular_mesh_ec.jl} (99%) diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl new file mode 100644 index 00000000000..b3342a727a1 --- /dev/null +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl @@ -0,0 +1,44 @@ +# !!! warning "Experimental features" + +using StartUpDG +using Trixi, OrdinaryDiffEq + +polydeg = 3 +rd = RefElemData(Tri(), polydeg) + +dg = DG(rd, nothing #= mortar =#, + SurfaceIntegralWeakForm(flux_ranocha), + VolumeIntegralFluxDifferencing(flux_ranocha)) + +equations = CompressibleEulerEquations2D(1.4) +initial_condition = initial_condition_weak_blast_wave +source_terms = nothing + +# example where we tag two separate boundary segments of the mesh +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_periodic=(true,true)) +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms) + +tspan = (0.0, 0.4) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = 0.5*dt0, save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary + +u = sol.u[end] +du = similar(u) +Trixi.rhs!(du, u, semi, tspan[end]) +entropy_timederivative = Trixi.analyze(:entropy_timederivative, du, u, tspan[end], + mesh, equations, dg, semi.cache) diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl similarity index 99% rename from examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl rename to examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl index c655f456539..0e9b5801cb8 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_flux_diff.jl +++ b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.4) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_2d_simplices.jl index f42425571d7..7de2a94ef6c 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_2d_simplices.jl @@ -54,15 +54,15 @@ end end @testset "2D simplicial flux differencing" begin - @trixi_testset "elixir_euler_triangular_mesh_flux_diff.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_flux_diff.jl"), + @trixi_testset "elixir_euler_triangular_mesh_ec.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_ec.jl"), l2 = [0.0023756965829858814, 0.002810713803967761, 0.0028107138039682894, 0.008040750705578132], linf = [0.004397202318891624, 0.00446064886127262, 0.004460648861263294, 0.012346721614063583] ) end - @trixi_testset "elixir_euler_sbp_triangular_mesh_flux_diff.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_flux_diff.jl"), + @trixi_testset "elixir_euler_sbp_triangular_mesh_ec.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_ec.jl"), l2 = [0.0019514080401385394, 0.00341875398076509, 0.0034187539807649155, 0.011829447744071755], linf = [0.004078990424579931, 0.007257990068658904, 0.007257990068565867, 0.027380769039135444] ) From 7ec2239c0ec5a987f2bbc0b49f0db994f920f6a4 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Wed, 7 Jul 2021 22:34:20 -0700 Subject: [PATCH 28/58] increasing tspan for simplicial tests --- .../elixir_euler_periodic_triangular_mesh.jl | 2 +- .../elixir_euler_quadrilateral_mesh.jl | 2 +- .../elixir_euler_triangular_mesh.jl | 2 +- .../elixir_euler_triangulate_pkg_mesh.jl | 4 ++-- test/test_examples_2d_simplices.jl | 24 +++++++++---------- 5 files changed, 17 insertions(+), 17 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl index 10b29282681..d20a6e6249a 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl @@ -17,7 +17,7 @@ mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms) -tspan = (0.0, 0.1) +tspan = (0.0, 0.4) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() diff --git a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl index 91342121a75..18c2c31db51 100644 --- a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl @@ -27,7 +27,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.4) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl index 5e277204353..931e0407be4 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl @@ -27,7 +27,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.4) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() diff --git a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl index c7845762fa0..45f7627acf8 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl @@ -6,7 +6,7 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tri(), polydeg) -dg = DG(rd, nothing #= mortar =#, +dg = DG(rd, nothing #= mortar =#, SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) @@ -29,7 +29,7 @@ semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms, boundary_conditions = boundary_conditions) -tspan = (0.0, 0.1) +tspan = (0.0, 0.2) ode = semidiscretize(semi, tspan) summary_callback = SummaryCallback() diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_2d_simplices.jl index 7de2a94ef6c..88e5f017736 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_2d_simplices.jl @@ -11,15 +11,15 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simpli @testset "2D simplicial mesh tests" begin @trixi_testset "elixir_euler_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh.jl"), - l2 = [0.0006456213233232335, 0.0012103605920880222, 0.0012103605920879606, 0.004127251610067376], - linf = [0.0007930980554167189, 0.0021736528649873854, 0.0021736528649864972, 0.005871873927952187] + l2 = [0.0013463253573454718, 0.0014235911638071127, 0.0014235911638076826, 0.00472192381034704], + linf = [0.0015248269221774802, 0.0020706908553849157, 0.0020706908553842496, 0.004913338290754243] ) end @trixi_testset "elixir_euler_periodic_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_periodic_triangular_mesh.jl"), - l2 = [0.000672767625167618, 0.001269847226694384, 0.0012698472266944028, 0.004177337699476258], - linf = [0.0007498340156470995, 0.0021716152870556726, 0.002171615287057893, 0.005873584107397356] + l2 = [0.0014986508075708323, 0.001528523420746786, 0.0015285234207473158, 0.004846505183839211], + linf = [0.0015062108658376872, 0.0019373508504645365, 0.0019373508504538783, 0.004742686826709086] ) end @@ -32,8 +32,8 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simpli @trixi_testset "elixir_euler_triangulate_pkg_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangulate_pkg_mesh.jl"), - l2 = [0.0001016711916046445, 0.00011071422293274785, 0.00011212482087451142, 0.00035893791736543447], - linf = [0.00035073781634786805, 0.00039815763002271076, 0.00041642100745109545, 0.0009481311054404529] + l2 = [0.00015405739868423074, 0.00014530283464035389, 0.00014870936695617315, 0.00044410650633679334], + linf = [0.00039269979059053384, 0.0004237090504681795, 0.000577877861525522, 0.0015066603278119928] ) end @@ -47,8 +47,8 @@ end @testset "2D quadrilateral tests (using simplicial DG code)" begin @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), - l2 = [0.00015946119543800883, 0.000264475476940273, 0.00026447547694017894, 0.0008996889622631928], - linf = [0.0002365475762040603, 0.00032922335054608176, 0.0003292233505463038, 0.0012473538592372435] + l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], + linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] ) end end @@ -56,15 +56,15 @@ end @testset "2D simplicial flux differencing" begin @trixi_testset "elixir_euler_triangular_mesh_ec.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_ec.jl"), - l2 = [0.0023756965829858814, 0.002810713803967761, 0.0028107138039682894, 0.008040750705578132], - linf = [0.004397202318891624, 0.00446064886127262, 0.004460648861263294, 0.012346721614063583] + l2 = [0.0027933352962091224, 0.0025258342972940733, 0.002525834297294699, 0.006605283437797167], + linf = [0.004922431030471852, 0.004290571244393693, 0.0042905712443874755, 0.01011072146850811] ) end @trixi_testset "elixir_euler_sbp_triangular_mesh_ec.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_ec.jl"), - l2 = [0.0019514080401385394, 0.00341875398076509, 0.0034187539807649155, 0.011829447744071755], - linf = [0.004078990424579931, 0.007257990068658904, 0.007257990068565867, 0.027380769039135444] + l2 = [0.0064085350751361654, 0.004884026905215297, 0.00488402690524701, 0.015465099079675847], + linf = [0.013903738198618676, 0.012497381091518989, 0.012497381090858628, 0.020986233863000248] ) end end From c834c68fe0f43abb4938497184e0f5fde3c55641 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Wed, 7 Jul 2021 23:13:44 -0700 Subject: [PATCH 29/58] removing cruft [skip ci] --- .../elixir_euler_periodic_triangular_mesh_ec.jl | 6 ------ 1 file changed, 6 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl index b3342a727a1..33bc311d547 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl +++ b/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl @@ -36,9 +36,3 @@ dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), dt = 0.5*dt0, save_everystep=false, callback=callbacks); summary_callback() # print the timer summary - -u = sol.u[end] -du = similar(u) -Trixi.rhs!(du, u, semi, tspan[end]) -entropy_timederivative = Trixi.analyze(:entropy_timederivative, du, u, tspan[end], - mesh, equations, dg, semi.cache) From 9178ff126f158574ea71a6c52eeb0e8bc5063397 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 12 Jul 2021 12:35:33 -0500 Subject: [PATCH 30/58] Apply suggestions from code review Co-authored-by: Hendrik Ranocha --- src/solvers/dg_multi/types_and_traits.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/solvers/dg_multi/types_and_traits.jl b/src/solvers/dg_multi/types_and_traits.jl index c75a8b196f2..222418c1041 100644 --- a/src/solvers/dg_multi/types_and_traits.jl +++ b/src/solvers/dg_multi/types_and_traits.jl @@ -18,7 +18,7 @@ Create a discontinuous Galerkin method which uses Optional: - approximation type of `approximation_type` (default is `Polynomial()`; `SBP()` also supported for -`Tri()`, `Quad()`, and `Hex()` element types). + `Tri()`, `Quad()`, and `Hex()` element types). """ function MultiDG(; polydeg::Integer, elem_type::AbstractElemShape, @@ -41,4 +41,4 @@ const SBPDGFluxDiff{Dim, Elem} = MultiDG{NDIMS, ElemType, <:SBP, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} -# Todo: simplices. Add traits for dispatch on affine/curved meshes here. \ No newline at end of file +# Todo: simplices. Add traits for dispatch on affine/curved meshes here. From dd0c6ad0ce7c8dddf03f38e4896016a78845c726 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Mon, 12 Jul 2021 10:38:26 -0700 Subject: [PATCH 31/58] fixing _ec name inconsistency in elixirs --- .../elixir_euler_sbp_triangular_mesh_ec.jl | 5 +++-- .../simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl | 5 +++-- examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl | 5 +++-- test/test_examples_2d_simplices.jl | 8 ++++---- test/test_examples_3d_simplices.jl | 4 ++-- 5 files changed, 15 insertions(+), 12 deletions(-) diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl index 0e9b5801cb8..a88a5f2a6e8 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl +++ b/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl @@ -6,9 +6,10 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tri(), SBP(), polydeg) -volume_flux = flux_ranocha +flux_ec = flux_ranocha dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralFluxDifferencing(volume_flux)) + SurfaceIntegralWeakForm(flux_ec), + VolumeIntegralFluxDifferencing(flux_ec)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl index d702c004951..d803a64b101 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl +++ b/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl @@ -6,9 +6,10 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tri(), polydeg) +flux_ec = flux_ranocha dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), - VolumeIntegralFluxDifferencing(flux_ranocha)) + SurfaceIntegralWeakForm(flux_ec), + VolumeIntegralFluxDifferencing(flux_ec)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl index 55241a5fe7e..7955b0b1732 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl +++ b/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl @@ -6,9 +6,10 @@ using Trixi, OrdinaryDiffEq polydeg = 3 rd = RefElemData(Tet(), polydeg) +flux_ec = flux_ranocha dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), - VolumeIntegralFluxDifferencing(flux_ranocha)) + SurfaceIntegralWeakForm(flux_ec), + VolumeIntegralFluxDifferencing(flux_ec)) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_2d_simplices.jl index 88e5f017736..2531f33a627 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_2d_simplices.jl @@ -56,15 +56,15 @@ end @testset "2D simplicial flux differencing" begin @trixi_testset "elixir_euler_triangular_mesh_ec.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_ec.jl"), - l2 = [0.0027933352962091224, 0.0025258342972940733, 0.002525834297294699, 0.006605283437797167], - linf = [0.004922431030471852, 0.004290571244393693, 0.0042905712443874755, 0.01011072146850811] + l2 = [0.008107539211003132, 0.007464472445092778, 0.007464472445093055, 0.01597648138530006], + linf = [0.012298218434060981, 0.013874789519390918, 0.013874789519420005, 0.040393065744379175] ) end @trixi_testset "elixir_euler_sbp_triangular_mesh_ec.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_ec.jl"), - l2 = [0.0064085350751361654, 0.004884026905215297, 0.00488402690524701, 0.015465099079675847], - linf = [0.013903738198618676, 0.012497381091518989, 0.012497381090858628, 0.020986233863000248] + l2 = [0.012858228819248307, 0.010649745431713896, 0.010649745431680024, 0.02628727578633061], + linf = [0.03733928157930677, 0.053088127555369624, 0.05308812755616854, 0.13379093830601718] ) end end diff --git a/test/test_examples_3d_simplices.jl b/test/test_examples_3d_simplices.jl index 6d7d5827382..844b102a312 100644 --- a/test/test_examples_3d_simplices.jl +++ b/test/test_examples_3d_simplices.jl @@ -21,8 +21,8 @@ end @trixi_testset "elixir_euler_tet_mesh_flux_diff.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh_flux_diff.jl"), - l2 = [0.04693516732847953, 0.0490148086446717, 0.048587225155397755, 0.04921946695784349, 0.12147656172990916], - linf = [0.10277064447821016, 0.12549628202719165, 0.11540362612261723, 0.12344556494598535, 0.3288299122603555] + l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], + linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] ) end From 5d887971f782c45188f122184ac7cb2a6489b7de Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 09:30:32 -0700 Subject: [PATCH 32/58] Apply suggestions from code review Co-authored-by: Michael Schlottke-Lakemper --- src/solvers/dg_multi/fluxdiff.jl | 23 ++++++++++------------- test/test_examples_2d_simplices.jl | 2 +- test/test_examples_3d_simplices.jl | 5 +---- 3 files changed, 12 insertions(+), 18 deletions(-) diff --git a/src/solvers/dg_multi/fluxdiff.jl b/src/solvers/dg_multi/fluxdiff.jl index 06ce9697614..d388264610a 100644 --- a/src/solvers/dg_multi/fluxdiff.jl +++ b/src/solvers/dg_multi/fluxdiff.jl @@ -50,8 +50,8 @@ function build_lazy_physical_derivative(element::Int, orientation::Int, end end -function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, - mesh::VertexMappedMesh, equations, dg::DG, cache) where {DG <: SBPDGFluxDiff} +function calc_volume_integral!(du, u::StructArray, volume_integral, + mesh::VertexMappedMesh, equations, dg::SBPDGFluxDiff, cache) rd = dg.basis @unpack local_values_threaded = cache @@ -72,8 +72,7 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr end -function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, - RealT, uEltype) where {DG <: PolyDGFluxDiff} where {Dim} +function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, RealT, uEltype) rd = dg.basis @unpack md = mesh @@ -86,7 +85,7 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end - Qrst_skew_Tr = map(A -> -.5*(A-A'), Qrst_hybridized) + Qrst_skew_Tr = map(A -> -0.5*(A-A'), Qrst_hybridized) nvars = nvariables(equations) @@ -109,8 +108,8 @@ function create_cache(mesh::VertexMappedMesh{Dim}, equations, dg::DG, local_values_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq), nvars)) for _ in 1:Threads.nthreads()] return (; md, Qrst_skew_Tr, VhP, Ph, invJ = inv.(md.J), - entropy_var_values, projected_entropy_var_values, entropy_projected_u_values, - u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) + entropy_var_values, projected_entropy_var_values, entropy_projected_u_values, + u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, @@ -154,16 +153,15 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr end end -function rhs!(du, u::StructArray, t, mesh, equations, - initial_condition, boundary_conditions::BC, source_terms::Source, - dg::PolyDGFluxDiff, cache) where {BC, Source} +function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions, + source_terms, dg::PolyDGFluxDiff, cache) - @trixi_timeit timer() "Reset du/dt" fill!(du,zero(eltype(du))) + @trixi_timeit timer() "Reset du/dt" fill!(du, zero(eltype(du))) @trixi_timeit timer() "entropy_projection!" entropy_projection!(cache, u, mesh, equations, dg) @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, - mesh, equations, dg, cache) + mesh, equations, dg, cache) # the following functions are the same as in VolumeIntegralWeakForm, and can be reused from dg.jl @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, mesh, equations, dg) @@ -179,4 +177,3 @@ function rhs!(du, u::StructArray, t, mesh, equations, return nothing end - diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_2d_simplices.jl index 2531f33a627..3ac39a60463 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_2d_simplices.jl @@ -8,7 +8,7 @@ include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_2d_dg") -@testset "2D simplicial mesh tests" begin +@testset "2D simplicial mesh" begin @trixi_testset "elixir_euler_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh.jl"), l2 = [0.0013463253573454718, 0.0014235911638071127, 0.0014235911638076826, 0.00472192381034704], diff --git a/test/test_examples_3d_simplices.jl b/test/test_examples_3d_simplices.jl index 844b102a312..a950374b16b 100644 --- a/test/test_examples_3d_simplices.jl +++ b/test/test_examples_3d_simplices.jl @@ -8,16 +8,13 @@ include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_3d_dg") -@testset "3D simplicial mesh tests" begin +@testset "3D simplicial mesh" begin @trixi_testset "elixir_euler_tet_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh.jl"), l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] ) end -end - -@testset "3D simplicial flux differencing tests" begin @trixi_testset "elixir_euler_tet_mesh_flux_diff.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh_flux_diff.jl"), From dbc8b858ca5e95dcda722e1b855eece390c2b46c Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 10:21:31 -0700 Subject: [PATCH 33/58] Update src/solvers/dg_multi/fluxdiff.jl Co-authored-by: Michael Schlottke-Lakemper --- src/solvers/dg_multi/fluxdiff.jl | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/solvers/dg_multi/fluxdiff.jl b/src/solvers/dg_multi/fluxdiff.jl index d388264610a..81c3e3c16af 100644 --- a/src/solvers/dg_multi/fluxdiff.jl +++ b/src/solvers/dg_multi/fluxdiff.jl @@ -129,7 +129,7 @@ function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, entropy_projected_u_values .= entropy2cons.(projected_entropy_var_values, equations) end -function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralFluxDifferencing, +function calc_volume_integral!(du, u::StructArray, volume_integral, mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) rd = dg.basis @@ -176,4 +176,3 @@ function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions, return nothing end - From 2f9857da52d0bcd240b313a29a5625adeb2f28df Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 13:18:15 -0500 Subject: [PATCH 34/58] adding hex elixir --- .../dg_multi/elixir_euler_hexahedral_mesh.jl | 44 +++++++++++++++++++ 1 file changed, 44 insertions(+) create mode 100644 examples/dg_multi/elixir_euler_hexahedral_mesh.jl diff --git a/examples/dg_multi/elixir_euler_hexahedral_mesh.jl b/examples/dg_multi/elixir_euler_hexahedral_mesh.jl new file mode 100644 index 00000000000..b3e232a19c1 --- /dev/null +++ b/examples/dg_multi/elixir_euler_hexahedral_mesh.jl @@ -0,0 +1,44 @@ +# !!! warning "Experimental features" + +using Trixi, OrdinaryDiffEq + +polydeg = 3 +rd = RefElemData(Hex(), polydeg) +dg = DG(rd, nothing #= mortar =#, + SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) + +equations = CompressibleEulerEquations3D(1.4) +initial_condition = initial_condition_convergence_test +source_terms = source_terms_convergence_test + +# example where we tag two separate boundary segments of the mesh +top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol +rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) +is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) +VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Hex(), 4) +mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) + +boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) +boundary_conditions = (; :top => boundary_condition_convergence_test, + :rest => boundary_condition_convergence_test) + +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms, + boundary_conditions = boundary_conditions) + +tspan = (0.0, 0.1) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = 0.5*dt0, save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary From 32cfac2580df67ac9e7eb176f5dab4015b01d315 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 14:34:29 -0500 Subject: [PATCH 35/58] removing cruft `solvers/dg_simplices` folder --- src/solvers/dg_simplices/dg.jl | 316 --------------------------------- 1 file changed, 316 deletions(-) delete mode 100644 src/solvers/dg_simplices/dg.jl diff --git a/src/solvers/dg_simplices/dg.jl b/src/solvers/dg_simplices/dg.jl deleted file mode 100644 index 63914696fb5..00000000000 --- a/src/solvers/dg_simplices/dg.jl +++ /dev/null @@ -1,316 +0,0 @@ -# !!! warning "Experimental features" - -# out <- A*x -mul_by!(A) = let A = A - @inline (out, x)->matmul!(out, A, x) -end - -# specialize for SBP operators since `matmul!` doesn't work for `UniformScaling` types. -mul_by!(A::UniformScaling) = let A = A - @inline (out, x)->mul!(out, A, x) -end - -# # Todo: simplices. Use `matmul!` for the following 2 functions until 5-arg `matmul!` once -# the hanging bug is fixed (see https://github.com/JuliaLinearAlgebra/Octavian.jl/issues/103). - -# out <- out + A * x -mul_by_accum!(A) = let A = A - @inline (out, x)->mul!(out, A, x, one(eltype(out)), one(eltype(out))) -end - -# out <- out + α * A * x -mul_by_accum!(A, α) = let A = A - @inline (out, x)->mul!(out, A, x, α, one(eltype(out))) -end - -const MultiDG{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = - DG{<:RefElemData{NDIMS, ElemType, ApproxType}, Mortar, SurfaceIntegral, VolumeIntegral} where {Mortar} - -const MultiDGWeakForm{NDIMS, ElemType, ApproxType} = - MultiDG{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} - -# these are necessary for pretty printing -polydeg(dg::MultiDG) = dg.basis.N -Base.summary(io::IO, dg::DG) where {DG <: MultiDG} = print(io, "MultiDG(polydeg=$(polydeg(dg)))") -Base.real(rd::RefElemData{NDIMS, Elem, ApproxType, Nfaces, RealT}) where {NDIMS, Elem, ApproxType, Nfaces, RealT} = RealT - -@inline eachdim(mesh) = Base.OneTo(ndims(mesh)) - -# iteration over all elements in a mesh -@inline ndofs(mesh::AbstractMeshData, dg::MultiDG, cache) = dg.basis.Np * mesh.md.num_elements -@inline eachelement(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(mesh.md.num_elements) - -# iteration over quantities in a single element -@inline each_face_node(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nfq) -@inline each_quad_node(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nq) - -# iteration over quantities over the entire mesh (dofs, quad nodes, face nodes). -@inline each_dof_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(ndofs(mesh, dg, cache)) -@inline each_quad_node_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nq * mesh.md.num_elements) -@inline each_face_node_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nfq * mesh.md.num_elements) - -# interface with semidiscretization_hyperbolic -wrap_array(u_ode::StructArray, mesh::AbstractMeshData, equations, dg::MultiDG, cache) = u_ode -function digest_boundary_conditions(boundary_conditions::NamedTuple{Keys,ValueTypes}, mesh::AbstractMeshData, - dg::MultiDG, cache) where {Keys,ValueTypes<:NTuple{N,Any}} where {N} - return boundary_conditions -end - -function allocate_coefficients(mesh::AbstractMeshData, equations, dg::MultiDG, cache) - md = mesh.md - nvars = nvariables(equations) - return StructArray{SVector{nvars, real(dg)}}(ntuple(_->similar(md.x),nvars)) -end - -function compute_coefficients!(u::StructArray, initial_condition, t, - mesh::AbstractMeshData{NDIMS}, equations, dg::MultiDG{NDIMS}, cache) where {NDIMS} - md = mesh.md - rd = dg.basis - @unpack u_values = cache - - @threaded for i in each_quad_node_global(mesh, dg, cache) - u_values[i] = initial_condition(getindex.(md.xyzq, i), t, equations) - end - - # compute L2 projection - StructArrays.foreachfield(mul_by!(rd.Pq), u, u_values) -end - -# interpolates from solution coefficients to face quadrature points -function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, - surface_integral, dg::MultiDG) - rd = dg.basis - @unpack u_face_values = cache - StructArrays.foreachfield(mul_by!(rd.Vf), u_face_values, u) -end - -function create_cache(mesh::VertexMappedMesh, equations, dg::DG, - RealT, uEltype) where {DG <: MultiDGWeakForm{NDIMS, ElemType}} where {NDIMS, ElemType} - - rd = dg.basis - md = mesh.md - - # volume quadrature weights, volume interpolation matrix - @unpack wq, Vq = rd - - # mass matrix, tuple of differentiation matrices - @unpack M, Drst, Pq = rd - - # ∫f(u) * dv/dx_i = ∑_j (Vq*D_i)'*diagm(wq)*(rstxyzJ[i,j].*f(Vq*u)) - weak_differentiation_matrices = map(D -> -M\((Vq*D)'*diagm(wq)), Drst) - - # for use with flux differencing schemes - Qrst = map(D->Pq'*M*D*Pq, Drst) - Qrst_skew_Tr = map(A -> -.5*(A-A'), Qrst) # Todo: simplices. Rename this in flux differencing PR - - nvars = nvariables(equations) - - # Todo: simplices. Factor common storage into a struct (MeshDataCache?) for reuse across solvers? - # storage for volume quadrature values, face quadrature values, flux values - u_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq, md.num_elements), nvars)) - u_face_values = StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nfq, md.num_elements), nvars)) - flux_face_values = similar(u_face_values) - - # local storage for fluxes - local_values_threaded = [StructArray{SVector{nvars, uEltype}}(ntuple(_->zeros(rd.Nq), nvars)) for _ in 1:Threads.nthreads()] - - return (; md, weak_differentiation_matrices, Qrst_skew_Tr, invJ = inv.(md.J), - u_values, local_values_threaded, u_face_values, flux_face_values) -end - -function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralWeakForm, - mesh::VertexMappedMesh, equations, dg::MultiDG{NDIMS}, cache) where {NDIMS} - - rd = dg.basis - md = mesh.md - @unpack weak_differentiation_matrices, u_values, local_values_threaded = cache - @unpack rstxyzJ = md # geometric terms - - # interpolate to quadrature points - StructArrays.foreachfield(mul_by!(rd.Vq), u_values, u) - - # Todo: simplices. Dispatch on curved/non-curved mesh types, this code only works for affine meshes (accessing rxJ[1,e],...) - @threaded for e in eachelement(mesh, dg, cache) - - flux_values = local_values_threaded[Threads.threadid()] - for i in eachdim(mesh) - flux_values .= flux.(view(u_values,:,e), i, equations) - for j in eachdim(mesh) - StructArrays.foreachfield(mul_by_accum!(weak_differentiation_matrices[j], rstxyzJ[i,j][1,e]), - view(du,:,e), flux_values) - end - end - end -end - -function calc_interface_flux!(cache, surface_integral::SurfaceIntegralWeakForm, - mesh::VertexMappedMesh, equations, dg::MultiDG{NDIMS}) where {NDIMS} - - @unpack surface_flux = surface_integral - md = mesh.md - @unpack mapM, mapP, nxyzJ, Jf = md - @unpack u_face_values, flux_face_values = cache - - @threaded for face_node_index in each_face_node_global(mesh, dg, cache) - - # inner (idM -> minus) and outer (idP -> plus) indices - idM, idP = mapM[face_node_index], mapP[face_node_index] - uM = u_face_values[idM] - - # compute flux if node is not a boundary node - if idM != idP - uP = u_face_values[idP] - normal = SVector{NDIMS}(getindex.(nxyzJ, idM)) / Jf[idM] - flux_face_values[idM] = surface_flux(uM, uP, normal, equations) * Jf[idM] - end - end -end - -# assumes cache.flux_face_values is computed and filled with -# for polyomial discretizations, use dense LIFT matrix for surface contributions. -function calc_surface_integral!(du, u, surface_integral::SurfaceIntegralWeakForm, - mesh::VertexMappedMesh, equations, - dg::MultiDG, cache) - rd = dg.basis - StructArrays.foreachfield(mul_by_accum!(rd.LIFT), du, cache.flux_face_values) -end - -# Specialize for nodal SBP discretizations. Uses that Vf*u = u[Fmask,:] -function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, surface_integral, - dg::MultiDG{NDIMS, <:AbstractElemShape, <:SBP}) where {NDIMS} - rd = dg.basis - @unpack Fmask = rd - @unpack u_face_values = cache - StructArrays.foreachfield((out, u)->out .= view(u, Fmask, :), u_face_values, u) -end - -# Specialize for nodal SBP discretizations. Uses that du = LIFT*u is equivalent to -# du[Fmask,:] .= u ./ rd.wq[rd.Fmask] -function calc_surface_integral!(du, u, surface_integral::SurfaceIntegralWeakForm, - mesh::VertexMappedMesh, equations, - dg::MultiDG{NDIMS,<:AbstractElemShape, <:SBP}, cache) where {NDIMS} - rd = dg.basis - md = mesh.md - @unpack flux_face_values = cache - @threaded for e in eachelement(mesh, dg, cache) - for i in each_face_node(mesh, dg, cache) - du[rd.Fmask[i],e] += flux_face_values[i,e] * rd.wf[i] / rd.wq[rd.Fmask[i]] - end - end -end - -# do nothing for periodic (default) boundary conditions -calc_boundary_flux!(cache, t, boundary_conditions::BoundaryConditionPeriodic, - mesh, equations, dg::MultiDG) = nothing - -# "lispy tuple programming" instead of for loop for type stability -function calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg::MultiDG) - - # peel off first boundary condition - calc_single_boundary_flux!(cache, t, first(boundary_conditions), first(keys(boundary_conditions)), - mesh, equations, dg) - - # recurse on the remainder of the boundary conditions - calc_boundary_flux!(cache, t, Base.tail(boundary_conditions), mesh, equations, dg) -end - -# terminate recursion -calc_boundary_flux!(cache, t, boundary_conditions::NamedTuple{(),Tuple{}}, - mesh, equations, dg::MultiDG) = nothing - -function calc_single_boundary_flux!(cache, t, boundary_condition, boundary_key, - mesh, equations, dg::MultiDG{NDIMS}) where {NDIMS} - - rd = dg.basis - md = mesh.md - @unpack u_face_values, flux_face_values = cache - @unpack xyzf, nxyzJ, Jf = md - @unpack surface_flux = dg.surface_integral - - # reshape face/normal arrays to have size = (num_points_on_face, num_faces_total). - # mesh.boundary_faces indexes into the columns of these face-reshaped arrays. - num_pts_per_face = rd.Nfq ÷ rd.Nfaces - num_faces_total = rd.Nfaces * md.num_elements - - # This function was originally defined as - # `reshape_by_face(u) = reshape(view(u, :), num_pts_per_face, num_faces_total)`. - # This results in allocations due to https://github.com/JuliaLang/julia/issues/36313. - # To avoid allocations, we use Tim Holy's suggestion: - # https://github.com/JuliaLang/julia/issues/36313#issuecomment-782336300. - reshape_by_face(u) = Base.ReshapedArray(u, (num_pts_per_face, num_faces_total), ()) - - u_face_values = reshape_by_face(u_face_values) - flux_face_values = reshape_by_face(flux_face_values) - Jf = reshape_by_face(Jf) - nxyzJ, xyzf = reshape_by_face.(nxyzJ), reshape_by_face.(xyzf) # broadcast over nxyzJ::NTuple{NDIMS,Matrix} - - # loop through boundary faces, which correspond to columns of reshaped u_face_values, ... - for f in mesh.boundary_faces[boundary_key] - for i in Base.OneTo(num_pts_per_face) - face_normal = SVector{NDIMS}(getindex.(nxyzJ, i, f)) / Jf[i,f] - face_coordinates = SVector{NDIMS}(getindex.(xyzf, i, f)) - flux_face_values[i,f] = boundary_condition(u_face_values[i,f], - face_normal, face_coordinates, t, - surface_flux, equations) * Jf[i,f] - end - end - - # Note: modifying the values of the reshaped array modifies the values of cache.flux_face_values. - # However, we don't have to re-reshape, since cache.flux_face_values still retains its original shape. -end - -# Todo: simplices. Specialize for modal DG on curved meshes using WADG -function invert_jacobian!(du, mesh::Mesh, equations, dg::MultiDG, - cache) where {Mesh <: AbstractMeshData} - @threaded for i in each_dof_global(mesh, dg, cache) - du[i] *= -cache.invJ[i] - end -end - -calc_sources!(du, u, t, source_terms::Nothing, - mesh::VertexMappedMesh, equations, dg::MultiDG, cache) = nothing - -# uses quadrature + projection to compute source terms. -function calc_sources!(du, u, t, source_terms::SourceTerms, - mesh::VertexMappedMesh, equations, dg::MultiDG, cache) where {SourceTerms} - - rd = dg.basis - md = mesh.md - @unpack Pq = rd - @unpack u_values, local_values_threaded = cache - @threaded for e in eachelement(mesh, dg, cache) - - source_values = local_values_threaded[Threads.threadid()] - - u_e = view(u_values, :, e) # u_values should already be computed from volume kernel - - for i in each_quad_node(mesh, dg, cache) - source_values[i] = source_terms(u_e[i], getindex.(md.xyzq, i, e), t, equations) - end - StructArrays.foreachfield(mul_by_accum!(Pq), view(du, :, e), source_values) - end -end - -function rhs!(du, u, t, mesh, equations, - initial_condition, boundary_conditions::BC, source_terms::Source, - dg::MultiDG, cache) where {BC, Source} - - @trixi_timeit timer() "Reset du/dt" fill!(du,zero(eltype(du))) - - @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, - mesh, equations, dg, cache) - - @trixi_timeit timer() "prolong2interfaces!" prolong2interfaces!(cache, u, mesh, equations, dg.surface_integral, dg) - - @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, mesh, equations, dg) - - @trixi_timeit timer() "calc_boundary_flux!" calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg) - - @trixi_timeit timer() "calc_surface_integral!" calc_surface_integral!(du, u, dg.surface_integral, mesh, equations, dg, cache) - - @trixi_timeit timer() "invert_jacobian" invert_jacobian!(du, mesh, equations, dg, cache) - - @trixi_timeit timer() "calc_sources!" calc_sources!(du, u, t, source_terms, mesh, equations, dg, cache) - - return nothing -end From 9ebfe2d13a5ed98b9c7ded4ee431cc242d8b5545 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 14:35:01 -0500 Subject: [PATCH 36/58] making StartUpDG an explicit dependency --- Project.toml | 1 + src/Trixi.jl | 32 ++++++++++++++------------------ 2 files changed, 15 insertions(+), 18 deletions(-) diff --git a/Project.toml b/Project.toml index e49343e6203..8ec6da5aac7 100644 --- a/Project.toml +++ b/Project.toml @@ -22,6 +22,7 @@ Printf = "de0858da-6303-5e67-8744-51eddeeeb8d7" RecipesBase = "3cdcf5f2-1ef4-517c-9805-6587b60abb01" Reexport = "189a3867-3050-52da-a836-e630ba90ab69" Requires = "ae029012-a4dd-5104-9daa-d747884805df" +StartUpDG = "472ebc20-7c99-4d4b-9470-8fde4e9faa0f" StaticArrays = "90137ffa-7385-5640-81b9-e52037218182" StrideArrays = "d1fa6d79-ef01-42a6-86c9-f7c551f8593b" StructArrays = "09ab397b-f2b6-538f-b94a-2f83cf4a842a" diff --git a/src/Trixi.jl b/src/Trixi.jl index f655b164d45..a9375ddf268 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -57,7 +57,6 @@ import SummationByPartsOperators: integrate, left_boundary_weight, right_boundar @reexport using SummationByPartsOperators: SummationByPartsOperators, derivative_operator - # TODO: include_optimized # This should be used everywhere (except to `include("interpolations.jl")`) # once the upstream issue https://github.com/timholy/Revise.jl/issues/634 @@ -195,6 +194,20 @@ export trixi_include, examples_dir, get_examples, default_example, default_examp export convergence_test, jacobian_fd, jacobian_ad_forward, linear_structure +# DGMulti solvers +using StartUpDG +@reexport using StartUpDG: StartUpDG, RefElemData, MeshData, Polynomial, SBP +@reexport using StartUpDG: Line, Tri, Quad, Hex, Tet, AbstractElemShape + +include("solvers/dg_multi/types_and_traits.jl") +export DGMulti +include("meshes/dg_multi_meshes.jl") +export AbstractMeshData, VertexMappedMesh +include("solvers/dg_multi/dg.jl") +export estimate_dt +include("solvers/dg_multi/flux_differencing.jl") +include("callbacks_step/analysis_dg_multi.jl") + # Visualization-related exports export PlotData1D, PlotData2D, getmesh, adapt_to_mesh_level!, adapt_to_mesh_level @@ -208,23 +221,6 @@ function __init__() @require Plots="91a5bcdd-55d7-5caf-9e0b-520d859cae80" begin using .Plots: plot, plot!, savefig end - - # require StartUpDG for triangular mesh solvers - @require StartUpDG="472ebc20-7c99-4d4b-9470-8fde4e9faa0f" begin - using .StartUpDG: RefElemData, MeshData, Polynomial, SBP - using .StartUpDG: Line, Tri, Quad, Hex, Tet, AbstractElemShape - - include("meshes/dg_multi_meshes.jl") - export AbstractMeshData, VertexMappedMesh - - include("solvers/dg_multi/types_and_traits.jl") - export MultiDG - - include("solvers/dg_multi/dg.jl") - include("solvers/dg_multi/fluxdiff.jl") - include("callbacks_step/analysis_dg_multi.jl") - end - end From 75c8f055212461cf78d4c82c1580bbf39b669f30 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 15:00:55 -0500 Subject: [PATCH 37/58] update elixirs - use `DGMulti` constructor - updating function signatures which involve `RefElemData` - remove `using StartUpDG` --- .../elixir_ape_sbp_triangular_mesh.jl | 13 +++++-------- .../dg_multi/elixir_euler_hexahedral_mesh.jl | 14 ++++++-------- .../elixir_euler_periodic_triangular_mesh.jl | 15 ++++++--------- ...lixir_euler_periodic_triangular_mesh_ec.jl | 15 +++++---------- .../elixir_euler_quadrilateral_mesh.jl | 15 ++++++--------- .../elixir_euler_sbp_triangular_mesh_ec.jl | 15 +++++---------- .../elixir_euler_tetrahedral_mesh.jl} | 13 +++++-------- .../elixir_euler_tetrahedral_mesh_ec.jl} | 19 ++++++++----------- .../elixir_euler_triangular_mesh.jl | 13 +++++-------- ...lixir_euler_triangular_mesh_convergence.jl | 13 +++++-------- .../elixir_euler_triangular_mesh_ec.jl | 15 +++++---------- .../elixir_euler_triangulate_pkg_mesh.jl | 13 +++++-------- 12 files changed, 66 insertions(+), 107 deletions(-) rename examples/{simplicial_2d_dg => dg_multi}/elixir_ape_sbp_triangular_mesh.jl (81%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_periodic_triangular_mesh.jl (71%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_periodic_triangular_mesh_ec.jl (74%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_quadrilateral_mesh.jl (80%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_sbp_triangular_mesh_ec.jl (79%) rename examples/{simplicial_3d_dg/elixir_euler_tet_mesh.jl => dg_multi/elixir_euler_tetrahedral_mesh.jl} (80%) rename examples/{simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl => dg_multi/elixir_euler_tetrahedral_mesh_ec.jl} (73%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_triangular_mesh.jl (81%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_triangular_mesh_convergence.jl (82%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_triangular_mesh_ec.jl (79%) rename examples/{simplicial_2d_dg => dg_multi}/elixir_euler_triangulate_pkg_mesh.jl (81%) diff --git a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl b/examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl similarity index 81% rename from examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl rename to examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl index 7c4f3785fe0..d22ae0474bc 100644 --- a/examples/simplicial_2d_dg/elixir_ape_sbp_triangular_mesh.jl +++ b/examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl @@ -1,12 +1,10 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), SBP(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), approximation_type = SBP(), + surface_integral = SurfaceIntegralWeakForm(FluxLaxFriedrichs()), + volume_integral = VolumeIntegralWeakForm()) v_mean_global = (0.25, 0.25) c_mean_global = 1.0 @@ -17,7 +15,7 @@ initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg) # If no boundary tags are specified, VertexMappedMesh will add the tag `:entire_boundary` boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) @@ -39,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = .5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_hexahedral_mesh.jl b/examples/dg_multi/elixir_euler_hexahedral_mesh.jl index b3e232a19c1..1b3a5e542b1 100644 --- a/examples/dg_multi/elixir_euler_hexahedral_mesh.jl +++ b/examples/dg_multi/elixir_euler_hexahedral_mesh.jl @@ -2,10 +2,9 @@ using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Hex(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Hex(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test @@ -15,8 +14,8 @@ source_terms = source_terms_convergence_test top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Hex(), 4) -mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) +vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(Hex(), 4) +mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -38,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl b/examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl similarity index 71% rename from examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl rename to examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl index d20a6e6249a..dbf1a8f8b30 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl @@ -1,19 +1,17 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) # equivalent to a "basis" -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_periodic=(true,true)) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_periodic=(true,true)) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms) @@ -29,7 +27,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl similarity index 74% rename from examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl rename to examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl index 33bc311d547..84ac3759f7b 100644 --- a/examples/simplicial_2d_dg/elixir_euler_periodic_triangular_mesh_ec.jl +++ b/examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl @@ -1,14 +1,10 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) - -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(flux_ranocha), - VolumeIntegralFluxDifferencing(flux_ranocha)) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(flux_ranocha), + volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_weak_blast_wave @@ -16,7 +12,7 @@ source_terms = nothing # example where we tag two separate boundary segments of the mesh vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_periodic=(true,true)) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_periodic=(true,true)) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms) @@ -32,7 +28,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl b/examples/dg_multi/elixir_euler_quadrilateral_mesh.jl similarity index 80% rename from examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl rename to examples/dg_multi/elixir_euler_quadrilateral_mesh.jl index 18c2c31db51..47c2e569af4 100644 --- a/examples/simplicial_2d_dg/elixir_euler_quadrilateral_mesh.jl +++ b/examples/dg_multi/elixir_euler_quadrilateral_mesh.jl @@ -1,12 +1,10 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Quad(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Quad(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -16,8 +14,8 @@ source_terms = source_terms_convergence_test top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(rd.elementType, 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_on_boundary = is_on_boundary) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Quad(), 4) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -39,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl similarity index 79% rename from examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl rename to examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl index a88a5f2a6e8..c495482dcd4 100644 --- a/examples/simplicial_2d_dg/elixir_euler_sbp_triangular_mesh_ec.jl +++ b/examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl @@ -1,15 +1,11 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), SBP(), polydeg) - flux_ec = flux_ranocha -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(flux_ec), - VolumeIntegralFluxDifferencing(flux_ec)) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), approximation_type = SBP(), + surface_integral = SurfaceIntegralWeakForm(flux_ec), + volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -20,7 +16,7 @@ top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) +mesh = VertexMappedMesh(VX, VY, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -42,7 +38,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5*estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl b/examples/dg_multi/elixir_euler_tetrahedral_mesh.jl similarity index 80% rename from examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl rename to examples/dg_multi/elixir_euler_tetrahedral_mesh.jl index 08f77b8d708..b47627feb87 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh.jl +++ b/examples/dg_multi/elixir_euler_tetrahedral_mesh.jl @@ -1,12 +1,10 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tet(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tet(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test @@ -17,7 +15,7 @@ top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 4) -mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) +mesh = VertexMappedMesh(VX, VY, VZ, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -39,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl b/examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl similarity index 73% rename from examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl rename to examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl index 7955b0b1732..1d5b2d6e944 100644 --- a/examples/simplicial_3d_dg/elixir_euler_tet_mesh_ec.jl +++ b/examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl @@ -1,15 +1,12 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tet(), polydeg) - flux_ec = flux_ranocha -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(flux_ec), - VolumeIntegralFluxDifferencing(flux_ec)) +dg = DGMulti(; polydeg = 3, elem_type = Tet(), + surface_integral = SurfaceIntegralWeakForm(flux_ec), + volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) + equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test @@ -19,8 +16,9 @@ source_terms = source_terms_convergence_test top_boundary(x, y, z, tol=50*eps()) = abs(z - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 2) -mesh = VertexMappedMesh(VX, VY, VZ, EToV, rd, is_on_boundary = is_on_boundary) +vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(Tet(), 2) +mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), + EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -42,7 +40,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl b/examples/dg_multi/elixir_euler_triangular_mesh.jl similarity index 81% rename from examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl rename to examples/dg_multi/elixir_euler_triangular_mesh.jl index 931e0407be4..dbf159925ad 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh.jl +++ b/examples/dg_multi/elixir_euler_triangular_mesh.jl @@ -1,12 +1,10 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -17,7 +15,7 @@ top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, is_on_boundary = is_on_boundary) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -39,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl b/examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl similarity index 82% rename from examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl rename to examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl index 9ebd780fc8a..29ef4d69db5 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_convergence.jl +++ b/examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl @@ -3,13 +3,11 @@ # run using # convergence_test(joinpath(examples_dir(), "triangular_mesh_2D", "elixir_euler_triangular_mesh_convergence.jl"), 4) -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxLaxFriedrichs()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxLaxFriedrichs()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -18,7 +16,7 @@ source_terms = source_terms_convergence_test # example where we tag two separate boundary segments of the mesh cells_per_dimension = (8,8) # detected by `extract_initial_resolution` for convergence tests vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), cells_per_dimension...) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd) +mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :entire_boundary => boundary_condition_convergence_test) @@ -39,7 +37,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_triangular_mesh_ec.jl similarity index 79% rename from examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl rename to examples/dg_multi/elixir_euler_triangular_mesh_ec.jl index d803a64b101..b14d7f87825 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangular_mesh_ec.jl +++ b/examples/dg_multi/elixir_euler_triangular_mesh_ec.jl @@ -1,15 +1,11 @@ # !!! warning "Experimental features" -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) - flux_ec = flux_ranocha -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(flux_ec), - VolumeIntegralFluxDifferencing(flux_ec)) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(flux_ec), + volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -20,7 +16,7 @@ top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(VX, VY, EToV, rd, is_on_boundary = is_on_boundary) +mesh = VertexMappedMesh(VX, VY, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, @@ -42,7 +38,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl similarity index 81% rename from examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl rename to examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl index 45f7627acf8..fb3c7c6c720 100644 --- a/examples/simplicial_2d_dg/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl @@ -1,13 +1,11 @@ # !!! warning "Experimental features" using Triangulate -using StartUpDG using Trixi, OrdinaryDiffEq -polydeg = 3 -rd = RefElemData(Tri(), polydeg) -dg = DG(rd, nothing #= mortar =#, - SurfaceIntegralWeakForm(FluxHLL()), VolumeIntegralWeakForm()) +dg = DGMulti(; polydeg = 3, elem_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test @@ -17,7 +15,7 @@ meshIO = StartUpDG.square_hole_domain(.25) # pre-defined Triangulate geometry in # the pre-defined Triangulate geometry in StartUpDG has integer boundary tags. this routine # assigns boundary faces based on these integer boundary tags. -mesh = VertexMappedMesh(meshIO, rd, Dict(:bottom=>1, :right=>2, :top=>3, :left=>4)) +mesh = VertexMappedMesh(meshIO, dg, Dict(:bottom=>1, :right=>2, :top=>3, :left=>4)) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :bottom => boundary_condition_convergence_test, @@ -41,7 +39,6 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) ############################################################################### # run the simulation -dt0 = StartUpDG.estimate_h(rd,mesh.md) / StartUpDG.inverse_trace_constant(rd) sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*dt0, save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary From cfb5a48b0615266dec55c4a96a6df360c55ad059 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 15:05:05 -0500 Subject: [PATCH 38/58] MultiDG -> DGMulti MultiDG -> DGMulti --- src/callbacks_step/analysis_dg_multi.jl | 10 ++-- src/meshes/dg_multi_meshes.jl | 19 ++++++++ src/solvers/dg_multi/dg.jl | 61 +++++++++++++----------- src/solvers/dg_multi/types_and_traits.jl | 27 ++++++----- 4 files changed, 73 insertions(+), 44 deletions(-) diff --git a/src/callbacks_step/analysis_dg_multi.jl b/src/callbacks_step/analysis_dg_multi.jl index fe7df162295..0684c210cdb 100644 --- a/src/callbacks_step/analysis_dg_multi.jl +++ b/src/callbacks_step/analysis_dg_multi.jl @@ -2,7 +2,7 @@ function calc_error_norms(func, u, t, analyzer, mesh::AbstractMeshData{NDIMS}, equations, initial_condition, - dg::MultiDG{NDIMS}, cache, cache_analysis) where {NDIMS} + dg::DGMulti{NDIMS}, cache, cache_analysis) where {NDIMS} rd = dg.basis md = mesh.md @unpack u_values = cache @@ -23,7 +23,7 @@ end function integrate(func::Func, u, mesh::AbstractMeshData, - equations, dg::MultiDG, cache; normalize=true) where {Func} + equations, dg::DGMulti, cache; normalize=true) where {Func} rd = dg.basis md = mesh.md @unpack u_values = cache @@ -39,7 +39,7 @@ function integrate(func::Func, u, end function analyze(::typeof(entropy_timederivative), du, u, t, - mesh::AbstractMeshData, equations, dg::MultiDG, cache) + mesh::AbstractMeshData, equations, dg::DGMulti, cache) rd = dg.basis md = mesh.md @@ -62,7 +62,7 @@ function analyze(::typeof(entropy_timederivative), du, u, t, end function create_cache_analysis(analyzer, mesh::AbstractMeshData, - equations, dg::MultiDG, cache, + equations, dg::DGMulti, cache, RealT, uEltype) md = mesh.md @@ -71,4 +71,4 @@ end SolutionAnalyzer(rd::RefElemData) = rd -nelements(mesh::AbstractMeshData, solver::MultiDG, cache) = mesh.md.num_elements +nelements(mesh::AbstractMeshData, solver::DGMulti, cache) = mesh.md.num_elements diff --git a/src/meshes/dg_multi_meshes.jl b/src/meshes/dg_multi_meshes.jl index bb3914e7346..ce24374f073 100644 --- a/src/meshes/dg_multi_meshes.jl +++ b/src/meshes/dg_multi_meshes.jl @@ -59,6 +59,16 @@ function VertexMappedMesh(vertex_coordinates::NTuple{NDIMS, Vector{Tv}}, EToV::A return VertexMappedMesh{NDIMS, typeof(rd.elementType), typeof(md), length(boundary_faces)}(md, boundary_faces) end +""" + VertexMappedMesh(vertex_coordinates, EToV, dg::DGMulti; + is_on_boundary = nothing, + is_periodic::NTuple{NDIMS, Bool} = ntuple(_->false, NDIMS)) where {NDIMS, Tv} + +Constructor which uses `dg::DGMulti` instead of `rd::RefElemData`. +""" +VertexMappedMesh(vertex_coordinates, EToV, dg::DGMulti; kwargs...) = + VertexMappedMesh(vertex_coordinates, EToV, dg.basis; kwargs...) + """ VertexMappedMesh(triangulateIO, rd::RefElemData{2, Tri}, boundary_dict::Dict{Symbol, Int}) @@ -75,6 +85,15 @@ function VertexMappedMesh(triangulateIO, rd::RefElemData{2, Tri}, boundary_dict: return VertexMappedMesh{2, typeof(rd.elementType), typeof(md), length(boundary_faces)}(md, boundary_faces) end +""" + VertexMappedMesh(triangulateIO, dg::DGMulti, boundary_dict::Dict{Symbol, Int}) + +Constructor which uses `dg::DGMulti` instead of `rd::RefElemData`. +""" +VertexMappedMesh(triangulateIO, dg::DGMulti, boundary_dict::Dict{Symbol, Int}) = + VertexMappedMesh(triangulateIO, dg.basis, boundary_dict) + +# old interface VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, args...; kwargs...) = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y), EToV, rd, args...; kwargs...) VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV, rd, args...; kwargs...) = diff --git a/src/solvers/dg_multi/dg.jl b/src/solvers/dg_multi/dg.jl index 23ae0b7bc2d..60236545ac4 100644 --- a/src/solvers/dg_multi/dg.jl +++ b/src/solvers/dg_multi/dg.jl @@ -26,33 +26,33 @@ end @inline eachdim(mesh) = Base.OneTo(ndims(mesh)) # iteration over all elements in a mesh -@inline ndofs(mesh::AbstractMeshData, dg::MultiDG, cache) = dg.basis.Np * mesh.md.num_elements -@inline eachelement(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(mesh.md.num_elements) +@inline ndofs(mesh::AbstractMeshData, dg::DGMulti, cache) = dg.basis.Np * mesh.md.num_elements +@inline eachelement(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(mesh.md.num_elements) # iteration over quantities in a single element -@inline each_face_node(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nfq) -@inline each_quad_node(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nq) +@inline each_face_node(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(dg.basis.Nfq) +@inline each_quad_node(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(dg.basis.Nq) # iteration over quantities over the entire mesh (dofs, quad nodes, face nodes). -@inline each_dof_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(ndofs(mesh, dg, cache)) -@inline each_quad_node_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nq * mesh.md.num_elements) -@inline each_face_node_global(mesh::AbstractMeshData, dg::MultiDG, cache) = Base.OneTo(dg.basis.Nfq * mesh.md.num_elements) +@inline each_dof_global(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(ndofs(mesh, dg, cache)) +@inline each_quad_node_global(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(dg.basis.Nq * mesh.md.num_elements) +@inline each_face_node_global(mesh::AbstractMeshData, dg::DGMulti, cache) = Base.OneTo(dg.basis.Nfq * mesh.md.num_elements) # interface with semidiscretization_hyperbolic -wrap_array(u_ode::StructArray, mesh::AbstractMeshData, equations, dg::MultiDG, cache) = u_ode +wrap_array(u_ode::StructArray, mesh::AbstractMeshData, equations, dg::DGMulti, cache) = u_ode function digest_boundary_conditions(boundary_conditions::NamedTuple{Keys,ValueTypes}, mesh::AbstractMeshData, - dg::MultiDG, cache) where {Keys,ValueTypes<:NTuple{N,Any}} where {N} + dg::DGMulti, cache) where {Keys,ValueTypes<:NTuple{N,Any}} where {N} return boundary_conditions end -function allocate_coefficients(mesh::AbstractMeshData, equations, dg::MultiDG, cache) +function allocate_coefficients(mesh::AbstractMeshData, equations, dg::DGMulti, cache) md = mesh.md nvars = nvariables(equations) return StructArray{SVector{nvars, real(dg)}}(ntuple(_->similar(md.x),nvars)) end function compute_coefficients!(u::StructArray, initial_condition, t, - mesh::AbstractMeshData{NDIMS}, equations, dg::MultiDG{NDIMS}, cache) where {NDIMS} + mesh::AbstractMeshData{NDIMS}, equations, dg::DGMulti{NDIMS}, cache) where {NDIMS} md = mesh.md rd = dg.basis @unpack u_values = cache @@ -65,16 +65,23 @@ function compute_coefficients!(u::StructArray, initial_condition, t, StructArrays.foreachfield(mul_by!(rd.Pq), u, u_values) end +# estimates the timestep based on polynomial degree and mesh. Does not account for physics (e.g., +# computes an estimate of `dt` based on the advection equation with constant unit advection speed). +function estimate_dt(dg::DGMulti, mesh::AbstractMeshData) + rd = dg.basis # RefElemData + return StartUpDG.estimate_h(rd, mesh.md) / StartUpDG.inverse_trace_constant(rd) +end + # interpolates from solution coefficients to face quadrature points function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, - surface_integral, dg::MultiDG) + surface_integral, dg::DGMulti) rd = dg.basis @unpack u_face_values = cache StructArrays.foreachfield(mul_by!(rd.Vf), u_face_values, u) end function create_cache(mesh::VertexMappedMesh, equations, dg::DG, - RealT, uEltype) where {DG <: Union{MultiDGWeakForm{NDIMS, ElemType}, SBPDGFluxDiff}} where {NDIMS, ElemType} + RealT, uEltype) where {DG <: Union{DGMultiWeakForm, DGMultiFluxDiff{ElemType, <:SBP}}} where {ElemType} rd = dg.basis md = mesh.md @@ -90,7 +97,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::DG, # for use with flux differencing schemes Qrst = map(D->Pq'*M*D*Pq, Drst) - Qrst_skew_Tr = map(A -> -.5*(A-A'), Qrst) # Todo: simplices. Rename this in flux differencing PR + Qrst_skew_Tr = map(A -> -0.5*(A-A'), Qrst) # Todo: simplices. Rename this in flux differencing PR nvars = nvariables(equations) @@ -108,7 +115,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::DG, end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralWeakForm, - mesh::VertexMappedMesh, equations, dg::MultiDG{NDIMS}, cache) where {NDIMS} + mesh::VertexMappedMesh, equations, dg::DGMulti{NDIMS}, cache) where {NDIMS} rd = dg.basis md = mesh.md @@ -133,7 +140,7 @@ function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegr end function calc_interface_flux!(cache, surface_integral::SurfaceIntegralWeakForm, - mesh::VertexMappedMesh, equations, dg::MultiDG{NDIMS}) where {NDIMS} + mesh::VertexMappedMesh, equations, dg::DGMulti{NDIMS}) where {NDIMS} @unpack surface_flux = surface_integral md = mesh.md @@ -159,14 +166,14 @@ end # for polyomial discretizations, use dense LIFT matrix for surface contributions. function calc_surface_integral!(du, u, surface_integral::SurfaceIntegralWeakForm, mesh::VertexMappedMesh, equations, - dg::MultiDG, cache) + dg::DGMulti, cache) rd = dg.basis StructArrays.foreachfield(mul_by_accum!(rd.LIFT), du, cache.flux_face_values) end # Specialize for nodal SBP discretizations. Uses that Vf*u = u[Fmask,:] function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, surface_integral, - dg::MultiDG{NDIMS, <:AbstractElemShape, <:SBP}) where {NDIMS} + dg::DGMulti{NDIMS, <:AbstractElemShape, <:SBP}) where {NDIMS} rd = dg.basis @unpack Fmask = rd @unpack u_face_values = cache @@ -177,7 +184,7 @@ end # du[Fmask,:] .= u ./ rd.wq[rd.Fmask] function calc_surface_integral!(du, u, surface_integral::SurfaceIntegralWeakForm, mesh::VertexMappedMesh, equations, - dg::MultiDG{NDIMS,<:AbstractElemShape, <:SBP}, cache) where {NDIMS} + dg::DGMulti{NDIMS,<:AbstractElemShape, <:SBP}, cache) where {NDIMS} rd = dg.basis md = mesh.md @unpack flux_face_values = cache @@ -190,10 +197,10 @@ end # do nothing for periodic (default) boundary conditions calc_boundary_flux!(cache, t, boundary_conditions::BoundaryConditionPeriodic, - mesh, equations, dg::MultiDG) = nothing + mesh, equations, dg::DGMulti) = nothing # "lispy tuple programming" instead of for loop for type stability -function calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg::MultiDG) +function calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg::DGMulti) # peel off first boundary condition calc_single_boundary_flux!(cache, t, first(boundary_conditions), first(keys(boundary_conditions)), @@ -205,10 +212,10 @@ end # terminate recursion calc_boundary_flux!(cache, t, boundary_conditions::NamedTuple{(),Tuple{}}, - mesh, equations, dg::MultiDG) = nothing + mesh, equations, dg::DGMulti) = nothing function calc_single_boundary_flux!(cache, t, boundary_condition, boundary_key, - mesh, equations, dg::MultiDG{NDIMS}) where {NDIMS} + mesh, equations, dg::DGMulti{NDIMS}) where {NDIMS} rd = dg.basis md = mesh.md @@ -250,7 +257,7 @@ end # Todo: simplices. Specialize for modal DG on curved meshes using WADG -function invert_jacobian!(du, mesh::Mesh, equations, dg::MultiDG, +function invert_jacobian!(du, mesh::Mesh, equations, dg::DGMulti, cache) where {Mesh <: AbstractMeshData} @threaded for i in each_dof_global(mesh, dg, cache) du[i] *= -cache.invJ[i] @@ -258,11 +265,11 @@ function invert_jacobian!(du, mesh::Mesh, equations, dg::MultiDG, end calc_sources!(du, u, t, source_terms::Nothing, - mesh::VertexMappedMesh, equations, dg::MultiDG, cache) = nothing + mesh::VertexMappedMesh, equations, dg::DGMulti, cache) = nothing # uses quadrature + projection to compute source terms. function calc_sources!(du, u, t, source_terms::SourceTerms, - mesh::VertexMappedMesh, equations, dg::MultiDG, cache) where {SourceTerms} + mesh::VertexMappedMesh, equations, dg::DGMulti, cache) where {SourceTerms} rd = dg.basis md = mesh.md @@ -283,7 +290,7 @@ end function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions::BC, source_terms::Source, - dg::MultiDG, cache) where {BC, Source} + dg::DGMulti, cache) where {BC, Source} @trixi_timeit timer() "Reset du/dt" fill!(du,zero(eltype(du))) diff --git a/src/solvers/dg_multi/types_and_traits.jl b/src/solvers/dg_multi/types_and_traits.jl index 062cc6ec1e9..2b8a9166e44 100644 --- a/src/solvers/dg_multi/types_and_traits.jl +++ b/src/solvers/dg_multi/types_and_traits.jl @@ -1,16 +1,16 @@ -# `MultiDG` refers to both multiple DG types (polynomial/SBP, simplices/quads/hexes) as well as +# `DGMulti` refers to both multiple DG types (polynomial/SBP, simplices/quads/hexes) as well as # the use of multi-dimensional operators in the solver. -const MultiDG{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = +const DGMulti{NDIMS, ElemType, ApproxType, SurfaceIntegral, VolumeIntegral} = DG{<:RefElemData{NDIMS, ElemType, ApproxType}, Mortar, SurfaceIntegral, VolumeIntegral} where {Mortar} # these are necessary for pretty printing -polydeg(dg::MultiDG) = dg.basis.N -Base.summary(io::IO, dg::DG) where {DG <: MultiDG} = print(io, "MultiDG(polydeg=$(polydeg(dg)))") +polydeg(dg::DGMulti) = dg.basis.N +Base.summary(io::IO, dg::DG) where {DG <: DGMulti} = print(io, "DGMulti(polydeg=$(polydeg(dg)))") Base.real(rd::RefElemData{NDIMS, Elem, ApproxType, Nfaces, RealT}) where {NDIMS, Elem, ApproxType, Nfaces, RealT} = RealT """ - MultiDG(; polydeg::Integer, + DGMulti(; polydeg::Integer, elem_type::AbstractElemShape, approximation_type=Polynomial(), surface_flux=flux_central, @@ -22,10 +22,10 @@ Create a discontinuous Galerkin method which uses - element type `elem_type` (`Tri()`, `Quad()`, `Tet()`, and `Hex()` currently supported) Optional: -- approximation type of `approximation_type` (default is `Polynomial()`; `SBP()` also supported for - `Tri()`, `Quad()`, and `Hex()` element types). +- `approximation_type` (default is `Polynomial()`; `SBP()` also supported for `Tri()`, `Quad()`, + and `Hex()` element types). """ -function MultiDG(; polydeg::Integer, +function DGMulti(; polydeg::Integer, elem_type::AbstractElemShape, approximation_type=Polynomial(), surface_flux=flux_central, @@ -36,14 +36,17 @@ function MultiDG(; polydeg::Integer, end # type aliases for dispatch purposes -const MultiDGWeakForm{NDIMS, ElemType, ApproxType} = - MultiDG{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} +const DGMultiWeakForm{ElemType, ApproxType} = + DGMulti{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} where {NDIMS} + +const DGMultiFluxDiff{ElemType, ApproxType} = + DGMulti{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS} const PolyDGFluxDiff{NDIMS, ElemType} = - MultiDG{NDIMS, ElemType, Polynomial, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} + DGMulti{NDIMS, ElemType, Polynomial, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} const SBPDGFluxDiff{Dim, Elem} = - MultiDG{NDIMS, ElemType, <:SBP, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} + DGMulti{NDIMS, ElemType, <:SBP, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} # Todo: simplices. Add traits for dispatch on affine/curved meshes here. From befd9f147ceb15cda385776a26d69a9cfe8d31e0 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 15:07:08 -0500 Subject: [PATCH 39/58] name clarifications + function specializiations --- .../{fluxdiff.jl => flux_differencing.jl} | 36 +++++++++++++------ 1 file changed, 25 insertions(+), 11 deletions(-) rename src/solvers/dg_multi/{fluxdiff.jl => flux_differencing.jl} (87%) diff --git a/src/solvers/dg_multi/fluxdiff.jl b/src/solvers/dg_multi/flux_differencing.jl similarity index 87% rename from src/solvers/dg_multi/fluxdiff.jl rename to src/solvers/dg_multi/flux_differencing.jl index 81c3e3c16af..010ca713677 100644 --- a/src/solvers/dg_multi/fluxdiff.jl +++ b/src/solvers/dg_multi/flux_differencing.jl @@ -1,12 +1,12 @@ """ - hadamard_sum_ATr!(du, ATr, volume_flux, u, skip_index=(i,j)->false) + hadamard_sum_A_transposed!(du, ATr, volume_flux, u, skip_index=(i,j)->false) Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the result into `du`. - `du`, `u` are vectors - `ATr` is the transpose of the flux differencing matrix `A`. The transpose is used for faster traversal since matrices are column major in Julia. """ -@inline function hadamard_sum_ATr!(du, ATr, volume_flux::VF, u, skip_index=(i,j)->false) where {VF} +@inline function hadamard_sum_A_transposed!(du, ATr, volume_flux, u, skip_index=(i,j)->false) rows, cols = axes(ATr) for i in cols u_i = u[i] @@ -20,7 +20,21 @@ Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the res end end -# For MultiDG implementations, we construct "physical" differentiation operators by taking linear +# Version of function without `skip_index`, as mentioned in +# https://github.com/trixi-framework/Trixi.jl/pull/695/files#r670403097 +@inline function hadamard_sum_A_transposed!(du, ATr, volume_flux::VF, u) where {VF} + rows, cols = axes(ATr) + for i in cols + u_i = u[i] + du_i = du[i] + for j in rows + du_i += ATr[j,i] * volume_flux(u_i, u[j]) + end + du[i] = du_i + end +end + +# For DGMulti implementations, we construct "physical" differentiation operators by taking linear # combinations of reference differentiation operators scaled by geometric change of variables terms. # We use LazyArrays.jl for lazy evaluation of physical differentiation operators, so that we can # compute linear combinations of differentiation operators on-the-fly in an allocation-free manner. @@ -50,7 +64,7 @@ function build_lazy_physical_derivative(element::Int, orientation::Int, end end -function calc_volume_integral!(du, u::StructArray, volume_integral, +function calc_volume_integral!(du, u, volume_integral, mesh::VertexMappedMesh, equations, dg::SBPDGFluxDiff, cache) rd = dg.basis @@ -65,7 +79,7 @@ function calc_volume_integral!(du, u::StructArray, volume_integral, u_local = view(u, :, e) for i in eachdim(mesh) Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) - hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local) + hadamard_sum_A_transposed!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local) end view(du, :, e) .+= rhs_local ./ rd.wq end @@ -78,10 +92,10 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, Rea @unpack md = mesh # Todo: simplices. Fix this when StartUpDG v0.11.0 releases: new API `Qrst_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd)` - if Dim == 2 + if ndims(mesh) == 2 Qr_hybridized, Qs_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized) - elseif Dim == 3 + elseif ndims(mesh) == 3 Qr_hybridized, Qs_hybridized, Qt_hybridized, VhP, Ph = StartUpDG.hybridized_SBP_operators(rd) Qrst_hybridized = (Qr_hybridized, Qs_hybridized, Qt_hybridized) end @@ -112,7 +126,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, Rea u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end -function entropy_projection!(cache, u::StructArray, mesh::VertexMappedMesh, +function entropy_projection!(cache, u, mesh::VertexMappedMesh, equations, dg::DG) where {DG <: PolyDGFluxDiff} rd = dg.basis @@ -147,14 +161,14 @@ function calc_volume_integral!(du, u::StructArray, volume_integral, u_local = view(entropy_projected_u_values, :, e) for i in eachdim(mesh) Qi_skew_Tr = build_lazy_physical_derivative(e, i, mesh, dg, cache) - hadamard_sum_ATr!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, skip_index) + hadamard_sum_A_transposed!(rhs_local, Qi_skew_Tr, volume_flux_oriented(i), u_local, skip_index) end StructArrays.foreachfield(mul_by_accum!(Ph), view(du, :, e), rhs_local) end end -function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions, - source_terms, dg::PolyDGFluxDiff, cache) +function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions::BC, + source_terms::Source, dg::PolyDGFluxDiff, cache) where {Source, BC} @trixi_timeit timer() "Reset du/dt" fill!(du, zero(eltype(du))) From cd15c5c39c4644d5aaf20c3938208bc9d0a9456e Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 15:07:29 -0500 Subject: [PATCH 40/58] combining dg_multi tests into a single `@testset` --- test/runtests.jl | 10 +--- test/test_examples_3d_simplices.jl | 28 ---------- ...simplices.jl => test_examples_dg_multi.jl} | 56 +++++++++++++------ 3 files changed, 41 insertions(+), 53 deletions(-) delete mode 100644 test/test_examples_3d_simplices.jl rename test/{test_examples_2d_simplices.jl => test_examples_dg_multi.jl} (54%) diff --git a/test/runtests.jl b/test/runtests.jl index 187918a0b7b..dd4aaf3b80c 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -50,13 +50,9 @@ const TRIXI_NTHREADS = clamp(Sys.CPU_THREADS, 2, 3) include("test_examples_2d_part3.jl") end - @time if TRIXI_TEST == "all" || TRIXI_TEST == "2d_simplices" - include("test_examples_2d_simplices.jl") - end - - @time if TRIXI_TEST == "all" || TRIXI_TEST == "3d_simplices" - include("test_examples_3d_simplices.jl") - end + @time if TRIXI_TEST == "all" || TRIXI_TEST == "dg_multi" + include("test_examples_dg_multi.jl") + end @time if TRIXI_TEST == "all" || TRIXI_TEST == "3d_part1" include("test_examples_3d_part1.jl") diff --git a/test/test_examples_3d_simplices.jl b/test/test_examples_3d_simplices.jl deleted file mode 100644 index a950374b16b..00000000000 --- a/test/test_examples_3d_simplices.jl +++ /dev/null @@ -1,28 +0,0 @@ -module TestExamples2DTri - -using Test -using Trixi - -include("test_trixi.jl") - -# pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory -EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_3d_dg") - -@testset "3D simplicial mesh" begin - @trixi_testset "elixir_euler_tet_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh.jl"), - l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], - linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] - ) - end - - @trixi_testset "elixir_euler_tet_mesh_flux_diff.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tet_mesh_flux_diff.jl"), - l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], - linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] - ) - end - -end - -end # module diff --git a/test/test_examples_2d_simplices.jl b/test/test_examples_dg_multi.jl similarity index 54% rename from test/test_examples_2d_simplices.jl rename to test/test_examples_dg_multi.jl index 3ac39a60463..0ff8d8add04 100644 --- a/test/test_examples_2d_simplices.jl +++ b/test/test_examples_dg_multi.jl @@ -1,4 +1,4 @@ -module TestExamples2DTri +module TestExamplesDGMulti using Test using Trixi @@ -6,13 +6,13 @@ using Trixi include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory -EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simplicial_2d_dg") +EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_multi") -@testset "2D simplicial mesh" begin +@testset "DGMulti" begin @trixi_testset "elixir_euler_triangular_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh.jl"), - l2 = [0.0013463253573454718, 0.0014235911638071127, 0.0014235911638076826, 0.00472192381034704], - linf = [0.0015248269221774802, 0.0020706908553849157, 0.0020706908553842496, 0.004913338290754243] + l2 = [0.0013463253573454783, 0.0014235911638070984, 0.0014235911638076622, 0.004721923810347086], + linf = [0.0015248269221803668, 0.002070690855385582, 0.002070690855385804, 0.004913338290754687] ) end @@ -37,23 +37,11 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "simpli ) end - @trixi_testset "2D simplicial convergence tests" begin + @trixi_testset "elixir_euler_triangular_mesh_convergence.jl" begin mean_convergence = convergence_test(@__MODULE__, joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_convergence.jl"), 2) @test isapprox(mean_convergence[:l2], [4.116645204366779, 4.06608993434891, 4.066089934205002, 4.114554671587996], rtol=0.05) end -end - -@testset "2D quadrilateral tests (using simplicial DG code)" begin - @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), - l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], - linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] - ) - end -end - -@testset "2D simplicial flux differencing" begin @trixi_testset "elixir_euler_triangular_mesh_ec.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_ec.jl"), l2 = [0.008107539211003132, 0.007464472445092778, 0.007464472445093055, 0.01597648138530006], @@ -67,6 +55,38 @@ end linf = [0.03733928157930677, 0.053088127555369624, 0.05308812755616854, 0.13379093830601718] ) end + + # # 2D quad mesh tests + # @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin + # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), + # l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], + # linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] + # ) + # end + + # # 3d tet/hex tests + # @trixi_testset "elixir_euler_tetrahedral_mesh.jl" begin + # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh.jl"), + # l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], + # linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] + # ) + # end + + # @trixi_testset "elixir_euler_tetrahedral_mesh_ec.jl" begin + # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh_ec.jl"), + # l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], + # linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] + # ) + # end + + # @trixi_testset "elixir_euler_hexahedral_mesh.jl" begin + # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_hexahedral_mesh.jl"), + # l2 = [0.00030580190715769566, 0.00040146357607439464, 0.00040146357607564597, 0.000401463576075708, 0.0015749412434154315], + # linf = [0.00036910287847780054, 0.00042659774184228283, 0.0004265977427213574, 0.00042659774250686233, 0.00143803344597071] + # ) + # end + + end end # module From 353cb157a7f209f47097ffed392ae99dc725cc8d Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 15:08:27 -0500 Subject: [PATCH 41/58] adding back commented out tests --- test/test_examples_dg_multi.jl | 57 +++++++++++++++++----------------- 1 file changed, 28 insertions(+), 29 deletions(-) diff --git a/test/test_examples_dg_multi.jl b/test/test_examples_dg_multi.jl index 0ff8d8add04..b7480e152d2 100644 --- a/test/test_examples_dg_multi.jl +++ b/test/test_examples_dg_multi.jl @@ -56,36 +56,35 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - # # 2D quad mesh tests - # @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin - # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), - # l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], - # linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] - # ) - # end - - # # 3d tet/hex tests - # @trixi_testset "elixir_euler_tetrahedral_mesh.jl" begin - # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh.jl"), - # l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], - # linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] - # ) - # end - - # @trixi_testset "elixir_euler_tetrahedral_mesh_ec.jl" begin - # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh_ec.jl"), - # l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], - # linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] - # ) - # end - - # @trixi_testset "elixir_euler_hexahedral_mesh.jl" begin - # @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_hexahedral_mesh.jl"), - # l2 = [0.00030580190715769566, 0.00040146357607439464, 0.00040146357607564597, 0.000401463576075708, 0.0015749412434154315], - # linf = [0.00036910287847780054, 0.00042659774184228283, 0.0004265977427213574, 0.00042659774250686233, 0.00143803344597071] - # ) - # end + # 2D quad mesh tests + @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), + l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], + linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] + ) + end + + # 3d tet/hex tests + @trixi_testset "elixir_euler_tetrahedral_mesh.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh.jl"), + l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], + linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] + ) + end + @trixi_testset "elixir_euler_tetrahedral_mesh_ec.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh_ec.jl"), + l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], + linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] + ) + end + + @trixi_testset "elixir_euler_hexahedral_mesh.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_hexahedral_mesh.jl"), + l2 = [0.00030580190715769566, 0.00040146357607439464, 0.00040146357607564597, 0.000401463576075708, 0.0015749412434154315], + linf = [0.00036910287847780054, 0.00042659774184228283, 0.0004265977427213574, 0.00042659774250686233, 0.00143803344597071] + ) + end end From 3f975cd504121922e6706b99fa80af3d44f08e2b Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 18:22:37 -0500 Subject: [PATCH 42/58] removing unnecessary annotations --- src/solvers/dg_multi/dg.jl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/solvers/dg_multi/dg.jl b/src/solvers/dg_multi/dg.jl index 60236545ac4..5a7104e940f 100644 --- a/src/solvers/dg_multi/dg.jl +++ b/src/solvers/dg_multi/dg.jl @@ -115,7 +115,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::DG, end function calc_volume_integral!(du, u::StructArray, volume_integral::VolumeIntegralWeakForm, - mesh::VertexMappedMesh, equations, dg::DGMulti{NDIMS}, cache) where {NDIMS} + mesh::VertexMappedMesh, equations, dg::DGMulti, cache) rd = dg.basis md = mesh.md From 952701ab5547b03cf7aef8539f05f2310812afd3 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Tue, 20 Jul 2021 18:37:40 -0500 Subject: [PATCH 43/58] renaming type aliases for DGMulti{...} - removed PolyDGFluxDiff, replaced with DGMultiFluxDiff{Polynomial} - removed SBPDGFluxDiff, replaced with DGMultiFluxDiff{SBP} --- src/solvers/dg_multi/dg.jl | 2 +- src/solvers/dg_multi/flux_differencing.jl | 17 ++++++++++------- src/solvers/dg_multi/types_and_traits.jl | 13 +++---------- 3 files changed, 14 insertions(+), 18 deletions(-) diff --git a/src/solvers/dg_multi/dg.jl b/src/solvers/dg_multi/dg.jl index 5a7104e940f..1fb8dcb64f8 100644 --- a/src/solvers/dg_multi/dg.jl +++ b/src/solvers/dg_multi/dg.jl @@ -81,7 +81,7 @@ function prolong2interfaces!(cache, u, mesh::AbstractMeshData, equations, end function create_cache(mesh::VertexMappedMesh, equations, dg::DG, - RealT, uEltype) where {DG <: Union{DGMultiWeakForm, DGMultiFluxDiff{ElemType, <:SBP}}} where {ElemType} + RealT, uEltype) where {DG <: Union{DGMultiWeakForm, DGMultiFluxDiff{<:SBP}}} rd = dg.basis md = mesh.md diff --git a/src/solvers/dg_multi/flux_differencing.jl b/src/solvers/dg_multi/flux_differencing.jl index 010ca713677..bcd179fc051 100644 --- a/src/solvers/dg_multi/flux_differencing.jl +++ b/src/solvers/dg_multi/flux_differencing.jl @@ -65,7 +65,7 @@ function build_lazy_physical_derivative(element::Int, orientation::Int, end function calc_volume_integral!(du, u, volume_integral, - mesh::VertexMappedMesh, equations, dg::SBPDGFluxDiff, cache) + mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:SBP}, cache) rd = dg.basis @unpack local_values_threaded = cache @@ -86,7 +86,7 @@ function calc_volume_integral!(du, u, volume_integral, end -function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, RealT, uEltype) +function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, RealT, uEltype) rd = dg.basis @unpack md = mesh @@ -101,7 +101,6 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, Rea end Qrst_skew_Tr = map(A -> -0.5*(A-A'), Qrst_hybridized) - nvars = nvariables(equations) # storage for all quadrature points (concatenated volume / face quadrature points) @@ -126,8 +125,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, Rea u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end -function entropy_projection!(cache, u, mesh::VertexMappedMesh, - equations, dg::DG) where {DG <: PolyDGFluxDiff} +function entropy_projection!(cache, u, mesh::VertexMappedMesh, equations, dg::DGMulti) rd = dg.basis @unpack Vq = rd @@ -144,7 +142,7 @@ function entropy_projection!(cache, u, mesh::VertexMappedMesh, end function calc_volume_integral!(du, u::StructArray, volume_integral, - mesh::VertexMappedMesh, equations, dg::PolyDGFluxDiff, cache) + mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, cache) rd = dg.basis md = mesh.md @@ -167,11 +165,16 @@ function calc_volume_integral!(du, u::StructArray, volume_integral, end end +# Specializes on Polynomial (e.g., modal) DG methods with a flux differencing volume kernel, e.g., +# an entropy conservative/stable discretization. For modal DG schemes, an extra `entropy_projection` +# is required (see https://doi.org/10.1016/j.jcp.2018.02.033, Section 4.3). function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions::BC, - source_terms::Source, dg::PolyDGFluxDiff, cache) where {Source, BC} + source_terms::Source, dg::DGMultiFluxDiff{Polynomial}, cache) where {Source, BC} @trixi_timeit timer() "Reset du/dt" fill!(du, zero(eltype(du))) + # this function evaluates the solution at volume and face quadrature points (which was previously + # done in `prolong2interfaces` and `calc_volume_integral`) @trixi_timeit timer() "entropy_projection!" entropy_projection!(cache, u, mesh, equations, dg) @trixi_timeit timer() "calc_volume_integral!" calc_volume_integral!(du, u, dg.volume_integral, diff --git a/src/solvers/dg_multi/types_and_traits.jl b/src/solvers/dg_multi/types_and_traits.jl index 2b8a9166e44..8202fa62542 100644 --- a/src/solvers/dg_multi/types_and_traits.jl +++ b/src/solvers/dg_multi/types_and_traits.jl @@ -35,18 +35,11 @@ function DGMulti(; polydeg::Integer, return DG(rd, nothing #= mortar =#, surface_integral, volume_integral) end -# type aliases for dispatch purposes -const DGMultiWeakForm{ElemType, ApproxType} = +# Type aliases. The first parameter is `ApproxType` since it is more commonly used for dispatch. +const DGMultiWeakForm{ApproxType, ElemType} = DGMulti{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralWeakForm} where {NDIMS} -const DGMultiFluxDiff{ElemType, ApproxType} = +const DGMultiFluxDiff{ApproxType, ElemType} = DGMulti{NDIMS, ElemType, ApproxType, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS} -const PolyDGFluxDiff{NDIMS, ElemType} = - DGMulti{NDIMS, ElemType, Polynomial, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} - -const SBPDGFluxDiff{Dim, Elem} = - DGMulti{NDIMS, ElemType, <:SBP, <:SurfaceIntegralWeakForm, <:VolumeIntegralFluxDifferencing} where {NDIMS, ElemType} - - # Todo: simplices. Add traits for dispatch on affine/curved meshes here. From 381f62670a0c81726aa559b0380dd86341f6a1f1 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 11:48:01 -0500 Subject: [PATCH 44/58] elem_type -> element_type --- src/solvers/dg_multi/types_and_traits.jl | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/solvers/dg_multi/types_and_traits.jl b/src/solvers/dg_multi/types_and_traits.jl index 8202fa62542..6d8eda4e524 100644 --- a/src/solvers/dg_multi/types_and_traits.jl +++ b/src/solvers/dg_multi/types_and_traits.jl @@ -11,7 +11,7 @@ Base.real(rd::RefElemData{NDIMS, Elem, ApproxType, Nfaces, RealT}) where {NDIMS, """ DGMulti(; polydeg::Integer, - elem_type::AbstractElemShape, + element_type::AbstractElemShape, approximation_type=Polynomial(), surface_flux=flux_central, surface_integral=SurfaceIntegralWeakForm(surface_flux), @@ -19,19 +19,19 @@ Base.real(rd::RefElemData{NDIMS, Elem, ApproxType, Nfaces, RealT}) where {NDIMS, Create a discontinuous Galerkin method which uses - approximations of polynomial degree `polydeg` -- element type `elem_type` (`Tri()`, `Quad()`, `Tet()`, and `Hex()` currently supported) +- element type `element_type` (`Tri()`, `Quad()`, `Tet()`, and `Hex()` currently supported) Optional: - `approximation_type` (default is `Polynomial()`; `SBP()` also supported for `Tri()`, `Quad()`, and `Hex()` element types). """ function DGMulti(; polydeg::Integer, - elem_type::AbstractElemShape, + element_type::AbstractElemShape, approximation_type=Polynomial(), surface_flux=flux_central, surface_integral=SurfaceIntegralWeakForm(surface_flux), volume_integral=VolumeIntegralWeakForm()) - rd = RefElemData(elem_type, approximation_type, polydeg) + rd = RefElemData(element_type, approximation_type, polydeg) return DG(rd, nothing #= mortar =#, surface_integral, volume_integral) end From 149bfc351ab9ed83a7c251e6f6c4462d06a7bf7e Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 11:48:12 -0500 Subject: [PATCH 45/58] minor formatting --- src/solvers/dg_multi/flux_differencing.jl | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/src/solvers/dg_multi/flux_differencing.jl b/src/solvers/dg_multi/flux_differencing.jl index bcd179fc051..6dfbb9ebcef 100644 --- a/src/solvers/dg_multi/flux_differencing.jl +++ b/src/solvers/dg_multi/flux_differencing.jl @@ -86,7 +86,8 @@ function calc_volume_integral!(du, u, volume_integral, end -function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, RealT, uEltype) +function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, + RealT, uEltype) rd = dg.basis @unpack md = mesh @@ -181,15 +182,19 @@ function rhs!(du, u, t, mesh, equations, initial_condition, boundary_conditions: mesh, equations, dg, cache) # the following functions are the same as in VolumeIntegralWeakForm, and can be reused from dg.jl - @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, mesh, equations, dg) + @trixi_timeit timer() "calc_interface_flux!" calc_interface_flux!(cache, dg.surface_integral, + mesh, equations, dg) - @trixi_timeit timer() "calc_boundary_flux!" calc_boundary_flux!(cache, t, boundary_conditions, mesh, equations, dg) + @trixi_timeit timer() "calc_boundary_flux!" calc_boundary_flux!(cache, t, boundary_conditions, + mesh, equations, dg) - @trixi_timeit timer() "calc_surface_integral!" calc_surface_integral!(du, u, dg.surface_integral, mesh, equations, dg, cache) + @trixi_timeit timer() "calc_surface_integral!" calc_surface_integral!(du, u, dg.surface_integral, + mesh, equations, dg, cache) @trixi_timeit timer() "invert_jacobian" invert_jacobian!(du, mesh, equations, dg, cache) - @trixi_timeit timer() "calc_sources!" calc_sources!(du, u, t, source_terms, mesh, equations, dg, cache) + @trixi_timeit timer() "calc_sources!" calc_sources!(du, u, t, source_terms, + mesh, equations, dg, cache) return nothing end From ffb5f027a1f49a9d82b473f3ecadce302c81dff9 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 11:57:33 -0500 Subject: [PATCH 46/58] consolidating elixirs and updating docs - switching from multiple elixirs to just using `trixi_include` to change parameters in a few elixirs - minor formatting minor formatting --- docs/src/meshes/mesh_data_meshes.md | 25 ++--- .../elixir_ape_sbp_triangular_mesh.jl | 42 --------- .../dg_multi/elixir_euler_hexahedral_mesh.jl | 42 --------- ...lixir_euler_periodic_triangular_mesh_ec.jl | 33 ------- .../elixir_euler_quadrilateral_mesh.jl | 42 --------- .../elixir_euler_sbp_triangular_mesh_ec.jl | 43 --------- .../elixir_euler_tetrahedral_mesh_ec.jl | 45 --------- ...lixir_euler_triangular_mesh_convergence.jl | 42 --------- .../elixir_euler_triangular_mesh_ec.jl | 43 --------- .../elixir_euler_triangulate_pkg_mesh.jl | 2 +- ...ar_mesh.jl => elixir_euler_weakform_2d.jl} | 6 +- ...al_mesh.jl => elixir_euler_weakform_3d.jl} | 4 +- ...l => elixir_euler_weakform_periodic_2d.jl} | 4 +- test/test_examples_dg_multi.jl | 92 +++++++++++-------- 14 files changed, 75 insertions(+), 390 deletions(-) delete mode 100644 examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl delete mode 100644 examples/dg_multi/elixir_euler_hexahedral_mesh.jl delete mode 100644 examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl delete mode 100644 examples/dg_multi/elixir_euler_quadrilateral_mesh.jl delete mode 100644 examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl delete mode 100644 examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl delete mode 100644 examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl delete mode 100644 examples/dg_multi/elixir_euler_triangular_mesh_ec.jl rename examples/dg_multi/{elixir_euler_triangular_mesh.jl => elixir_euler_weakform_2d.jl} (88%) rename examples/dg_multi/{elixir_euler_tetrahedral_mesh.jl => elixir_euler_weakform_3d.jl} (93%) rename examples/dg_multi/{elixir_euler_periodic_triangular_mesh.jl => elixir_euler_weakform_periodic_2d.jl} (93%) diff --git a/docs/src/meshes/mesh_data_meshes.md b/docs/src/meshes/mesh_data_meshes.md index 0d227ca8499..2be3e4d0755 100644 --- a/docs/src/meshes/mesh_data_meshes.md +++ b/docs/src/meshes/mesh_data_meshes.md @@ -113,19 +113,20 @@ approximation on a triangle. There are also several parameters which can be twea [StartUpDG.jl docs](https://jlchan.github.io/StartUpDG.jl/dev/RefElemData/#RefElemData-based-on-SBP-finite-differences). Trixi will also specialize certain parts of the solver based on the `SBP` approximation type. -## Trixi elixirs on simplicial meshes +## Trixi elixirs on simplicial and tensor product element meshes -Example elixirs on simplicial meshes can be found in the `examples/simplicial_mesh` folder. -Some key elixirs to look at: +Example elixirs on triangular, quadrilateral, tetrahedral, and simplicial meshes can be found in +the `examples/dg_multi` folder. Some key elixirs to look at: -* `elixir_euler_triangular_mesh.jl`: basic weak form DG discretization on a uniform triangular mesh. -* `elixir_euler_periodic_triangular_mesh.jl`: same as above, but enforces periodicity in the ``x,y`` directions. +* `elixir_euler_weakform_2d.jl`: basic weak form DG discretization on a uniform triangular mesh. + Changing `element_type = Quad()` or `approximation_type = SBP()` will switch to a quadrilateral mesh + or an SBP-type discretization. Changing `surface_integral = SurfaceIntegralWeakForm(flux_ec)` and + `volume_integral = VolumeIntegralFluxDifferencing(flux_ec)` for some entropy conservative flux + (e.g., `flux_chandrashekar` or `flux_ranocha`) will switch to an entropy conservative formulation. * `elixir_euler_triangulate_pkg_mesh.jl`: uses a `TriangulateIO` unstructured mesh generated by [Triangulate.jl](https://github.com/JuliaGeometry/Triangulate.jl). -* `elixir_ape_sbp_triangular_mesh.jl`: uses a multi-dimensional SBP discretization in weak form. -* `elixir_euler_tet_mesh.jl`: basic weak form DG discretization on a uniform tet mesh. - -We also have support for flux differencing on simplicial meshes: -* `elixir_euler_triangular_mesh_ec.jl`: Modal DG discretization with flux differencing on a uniform triangular mesh. -* `elixir_euler_sbp_triangular_mesh_ec.jl`: SBP-DG discretization with flux differencing on a uniform triangular mesh. -* `elixir_euler_tet_mesh_ec.jl`: Modal DG discretization with flux differencing on a uniform tetrahedral mesh. +* `elixir_euler_weakform_3d.jl`: basic weak form DG discretization on a uniform tetrahedral mesh. + Changing `element_type = Hex()` will switch to a hexahedral mesh. Changing + `surface_integral = SurfaceIntegralWeakForm(flux_ec)` and + `volume_integral = VolumeIntegralFluxDifferencing(flux_ec)` for some entropy conservative flux + (e.g., `flux_chandrashekar` or `flux_ranocha`) will switch to an entropy conservative formulation. diff --git a/examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl b/examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl deleted file mode 100644 index d22ae0474bc..00000000000 --- a/examples/dg_multi/elixir_ape_sbp_triangular_mesh.jl +++ /dev/null @@ -1,42 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -dg = DGMulti(; polydeg = 3, elem_type = Tri(), approximation_type = SBP(), - surface_integral = SurfaceIntegralWeakForm(FluxLaxFriedrichs()), - volume_integral = VolumeIntegralWeakForm()) - -v_mean_global = (0.25, 0.25) -c_mean_global = 1.0 -rho_mean_global = 1.0 -equations = AcousticPerturbationEquations2D(v_mean_global, c_mean_global, rho_mean_global) - -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg) - -# If no boundary tags are specified, VertexMappedMesh will add the tag `:entire_boundary` -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :entire_boundary => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.1) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_hexahedral_mesh.jl b/examples/dg_multi/elixir_euler_hexahedral_mesh.jl deleted file mode 100644 index 1b3a5e542b1..00000000000 --- a/examples/dg_multi/elixir_euler_hexahedral_mesh.jl +++ /dev/null @@ -1,42 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -dg = DGMulti(; polydeg = 3, elem_type = Hex(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) - -equations = CompressibleEulerEquations3D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol -rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) -is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(Hex(), 4) -mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), EToV, dg, is_on_boundary = is_on_boundary) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :top => boundary_condition_convergence_test, - :rest => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.1) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl deleted file mode 100644 index 84ac3759f7b..00000000000 --- a/examples/dg_multi/elixir_euler_periodic_triangular_mesh_ec.jl +++ /dev/null @@ -1,33 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -dg = DGMulti(; polydeg = 3, elem_type = Tri(), - surface_integral = SurfaceIntegralWeakForm(flux_ranocha), - volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha)) - -equations = CompressibleEulerEquations2D(1.4) -initial_condition = initial_condition_weak_blast_wave -source_terms = nothing - -# example where we tag two separate boundary segments of the mesh -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_periodic=(true,true)) -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms) - -tspan = (0.0, 0.4) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_quadrilateral_mesh.jl b/examples/dg_multi/elixir_euler_quadrilateral_mesh.jl deleted file mode 100644 index 47c2e569af4..00000000000 --- a/examples/dg_multi/elixir_euler_quadrilateral_mesh.jl +++ /dev/null @@ -1,42 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -dg = DGMulti(; polydeg = 3, elem_type = Quad(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) - -equations = CompressibleEulerEquations2D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Quad(), 4) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_on_boundary = is_on_boundary) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :top => boundary_condition_convergence_test, - :rest => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.4) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl deleted file mode 100644 index c495482dcd4..00000000000 --- a/examples/dg_multi/elixir_euler_sbp_triangular_mesh_ec.jl +++ /dev/null @@ -1,43 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -flux_ec = flux_ranocha -dg = DGMulti(; polydeg = 3, elem_type = Tri(), approximation_type = SBP(), - surface_integral = SurfaceIntegralWeakForm(flux_ec), - volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) - -equations = CompressibleEulerEquations2D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(VX, VY, EToV, dg, is_on_boundary = is_on_boundary) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :top => boundary_condition_convergence_test, - :rest => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.4) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5*estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl b/examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl deleted file mode 100644 index 1d5b2d6e944..00000000000 --- a/examples/dg_multi/elixir_euler_tetrahedral_mesh_ec.jl +++ /dev/null @@ -1,45 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -flux_ec = flux_ranocha -dg = DGMulti(; polydeg = 3, elem_type = Tet(), - surface_integral = SurfaceIntegralWeakForm(flux_ec), - volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) - - -equations = CompressibleEulerEquations3D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -top_boundary(x, y, z, tol=50*eps()) = abs(z - 1) < tol -rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) -is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(Tet(), 2) -mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), - EToV, dg, is_on_boundary = is_on_boundary) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :top => boundary_condition_convergence_test, - :rest => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.25) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl b/examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl deleted file mode 100644 index 29ef4d69db5..00000000000 --- a/examples/dg_multi/elixir_euler_triangular_mesh_convergence.jl +++ /dev/null @@ -1,42 +0,0 @@ -# !!! warning "Experimental features" - -# run using -# convergence_test(joinpath(examples_dir(), "triangular_mesh_2D", "elixir_euler_triangular_mesh_convergence.jl"), 4) - -using Trixi, OrdinaryDiffEq - -dg = DGMulti(; polydeg = 3, elem_type = Tri(), - surface_integral = SurfaceIntegralWeakForm(FluxLaxFriedrichs()), - volume_integral = VolumeIntegralWeakForm()) - -equations = CompressibleEulerEquations2D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -cells_per_dimension = (8,8) # detected by `extract_initial_resolution` for convergence tests -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), cells_per_dimension...) -mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :entire_boundary => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.25) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_triangular_mesh_ec.jl b/examples/dg_multi/elixir_euler_triangular_mesh_ec.jl deleted file mode 100644 index b14d7f87825..00000000000 --- a/examples/dg_multi/elixir_euler_triangular_mesh_ec.jl +++ /dev/null @@ -1,43 +0,0 @@ -# !!! warning "Experimental features" - -using Trixi, OrdinaryDiffEq - -flux_ec = flux_ranocha -dg = DGMulti(; polydeg = 3, elem_type = Tri(), - surface_integral = SurfaceIntegralWeakForm(flux_ec), - volume_integral = VolumeIntegralFluxDifferencing(flux_ec)) - -equations = CompressibleEulerEquations2D(1.4) -initial_condition = initial_condition_convergence_test -source_terms = source_terms_convergence_test - -# example where we tag two separate boundary segments of the mesh -top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -VX, VY, EToV = StartUpDG.uniform_mesh(Tri(), 4) -mesh = VertexMappedMesh(VX, VY, EToV, dg, is_on_boundary = is_on_boundary) - -boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) -boundary_conditions = (; :top => boundary_condition_convergence_test, - :rest => boundary_condition_convergence_test) - -semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, - source_terms = source_terms, - boundary_conditions = boundary_conditions) - -tspan = (0.0, 0.4) -ode = semidiscretize(semi, tspan) - -summary_callback = SummaryCallback() -alive_callback = AliveCallback(alive_interval=10) -analysis_interval = 100 -analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) -callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) - -############################################################################### -# run the simulation - -sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); -summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl index fb3c7c6c720..0ab3261c70f 100644 --- a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl @@ -3,7 +3,7 @@ using Triangulate using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, elem_type = Tri(), +dg = DGMulti(; polydeg = 3, element_type = Tri(), surface_integral = SurfaceIntegralWeakForm(FluxHLL()), volume_integral = VolumeIntegralWeakForm()) diff --git a/examples/dg_multi/elixir_euler_triangular_mesh.jl b/examples/dg_multi/elixir_euler_weakform_2d.jl similarity index 88% rename from examples/dg_multi/elixir_euler_triangular_mesh.jl rename to examples/dg_multi/elixir_euler_weakform_2d.jl index dbf159925ad..b9866e6b2f4 100644 --- a/examples/dg_multi/elixir_euler_triangular_mesh.jl +++ b/examples/dg_multi/elixir_euler_weakform_2d.jl @@ -2,7 +2,7 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, elem_type = Tri(), +dg = DGMulti(; polydeg = 3, element_type = Tri(), approximation_type = Polynomial(), surface_integral = SurfaceIntegralWeakForm(FluxHLL()), volume_integral = VolumeIntegralWeakForm()) @@ -14,7 +14,9 @@ source_terms = source_terms_convergence_test top_boundary(x,y,tol=50*eps()) = abs(y-1) top_boundary, :rest => rest_of_boundary) -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) + +cells_per_dimension = (8,8) # detected by `extract_initial_resolution` for convergence tests +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, cells_per_dimension...) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) diff --git a/examples/dg_multi/elixir_euler_tetrahedral_mesh.jl b/examples/dg_multi/elixir_euler_weakform_3d.jl similarity index 93% rename from examples/dg_multi/elixir_euler_tetrahedral_mesh.jl rename to examples/dg_multi/elixir_euler_weakform_3d.jl index b47627feb87..ee05b28082e 100644 --- a/examples/dg_multi/elixir_euler_tetrahedral_mesh.jl +++ b/examples/dg_multi/elixir_euler_weakform_3d.jl @@ -2,7 +2,7 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, elem_type = Tet(), +dg = DGMulti(; polydeg = 3, element_type = Tet(), surface_integral = SurfaceIntegralWeakForm(FluxHLL()), volume_integral = VolumeIntegralWeakForm()) @@ -14,7 +14,7 @@ source_terms = source_terms_convergence_test top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -VX, VY, VZ, EToV = StartUpDG.uniform_mesh(Tet(), 4) +VX, VY, VZ, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, 4) mesh = VertexMappedMesh(VX, VY, VZ, EToV, dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) diff --git a/examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl b/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl similarity index 93% rename from examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl rename to examples/dg_multi/elixir_euler_weakform_periodic_2d.jl index dbf1a8f8b30..f7b8dca25d2 100644 --- a/examples/dg_multi/elixir_euler_periodic_triangular_mesh.jl +++ b/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl @@ -2,7 +2,7 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, elem_type = Tri(), +dg = DGMulti(; polydeg = 3, element_type = Tri(), surface_integral = SurfaceIntegralWeakForm(FluxHLL()), volume_integral = VolumeIntegralWeakForm()) @@ -10,7 +10,7 @@ equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test source_terms = source_terms_convergence_test -vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(Tri(), 4) +vertex_coordinates_x, vertex_coordinates_y, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, 4) mesh = VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, dg, is_periodic=(true,true)) semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, source_terms = source_terms) diff --git a/test/test_examples_dg_multi.jl b/test/test_examples_dg_multi.jl index b7480e152d2..75c7d9e7dc1 100644 --- a/test/test_examples_dg_multi.jl +++ b/test/test_examples_dg_multi.jl @@ -9,78 +9,92 @@ include("test_trixi.jl") EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_multi") @testset "DGMulti" begin - @trixi_testset "elixir_euler_triangular_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh.jl"), + @trixi_testset "Euler triangular mesh" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + cells_per_dimension = (4,4), l2 = [0.0013463253573454783, 0.0014235911638070984, 0.0014235911638076622, 0.004721923810347086], linf = [0.0015248269221803668, 0.002070690855385582, 0.002070690855385804, 0.004913338290754687] ) end - @trixi_testset "elixir_euler_periodic_triangular_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_periodic_triangular_mesh.jl"), - l2 = [0.0014986508075708323, 0.001528523420746786, 0.0015285234207473158, 0.004846505183839211], - linf = [0.0015062108658376872, 0.0019373508504645365, 0.0019373508504538783, 0.004742686826709086] - ) - end - - @trixi_testset "elixir_ape_sbp_triangular_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_ape_sbp_triangular_mesh.jl"), - l2 = [0.13498182674793963, 0.13498182674793793, 0.10409926243751662, 0.0, 0.0, 0.0, 0.0], - linf = [0.326623183281191, 0.3266231832808133, 0.349817130019491, 0.0, 0.0, 0.0, 0.0] + @trixi_testset "Euler triangular mesh SBP" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + cells_per_dimension = (4,4), + approximation_type = SBP(), + l2 = [0.007465048853079056, 0.005297478943323888, 0.005297478943334149, 0.014701766352428895], + linf = [0.02149035033755564, 0.0135293837651278, 0.013529383764659286, 0.03269081948752639] ) end - @trixi_testset "elixir_euler_triangulate_pkg_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangulate_pkg_mesh.jl"), - l2 = [0.00015405739868423074, 0.00014530283464035389, 0.00014870936695617315, 0.00044410650633679334], - linf = [0.00039269979059053384, 0.0004237090504681795, 0.000577877861525522, 0.0015066603278119928] + @trixi_testset "Euler quadrilateral mesh.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + cells_per_dimension = (4,4), + element_type = Quad(), + l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], + linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] ) end - @trixi_testset "elixir_euler_triangular_mesh_convergence.jl" begin - mean_convergence = convergence_test(@__MODULE__, joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_convergence.jl"), 2) - @test isapprox(mean_convergence[:l2], [4.116645204366779, 4.06608993434891, 4.066089934205002, 4.114554671587996], rtol=0.05) - end - - @trixi_testset "elixir_euler_triangular_mesh_ec.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangular_mesh_ec.jl"), + @trixi_testset "Euler triangular mesh EC" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + cells_per_dimension = (4,4), + volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), + surface_integral = SurfaceIntegralWeakForm(flux_ranocha), l2 = [0.008107539211003132, 0.007464472445092778, 0.007464472445093055, 0.01597648138530006], linf = [0.012298218434060981, 0.013874789519390918, 0.013874789519420005, 0.040393065744379175] ) end - @trixi_testset "elixir_euler_sbp_triangular_mesh_ec.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_sbp_triangular_mesh_ec.jl"), + @trixi_testset "Euler triangular mesh SBP EC" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + cells_per_dimension = (4,4), + volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), + surface_integral = SurfaceIntegralWeakForm(flux_ranocha), + approximation_type = SBP(), l2 = [0.012858228819248307, 0.010649745431713896, 0.010649745431680024, 0.02628727578633061], linf = [0.03733928157930677, 0.053088127555369624, 0.05308812755616854, 0.13379093830601718] ) end - # 2D quad mesh tests - @trixi_testset "elixir_euler_quadrilateral_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_quadrilateral_mesh.jl"), - l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], - linf = [0.0004970396373780162, 0.0004059109438805386, 0.00040591094388231497, 0.0014247618507141624] + @trixi_testset "Euler triangular mesh convergence" begin + mean_convergence = convergence_test(@__MODULE__, joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), 2) + @test isapprox(mean_convergence[:l2], [4.2498632232077815, 4.133717042428824, 4.133717042041395, 4.086223177072245], rtol=0.05) + end + + @trixi_testset "Euler periodic triangular mesh" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_2d.jl"), + l2 = [0.0014986508075708323, 0.001528523420746786, 0.0015285234207473158, 0.004846505183839211], + linf = [0.0015062108658376872, 0.0019373508504645365, 0.0019373508504538783, 0.004742686826709086] + ) + end + + @trixi_testset "Euler with Triangulate.jl mesh" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangulate_pkg_mesh.jl"), + l2 = [0.00015405739868423074, 0.00014530283464035389, 0.00014870936695617315, 0.00044410650633679334], + linf = [0.00039269979059053384, 0.0004237090504681795, 0.000577877861525522, 0.0015066603278119928] ) end # 3d tet/hex tests - @trixi_testset "elixir_euler_tetrahedral_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh.jl"), + @trixi_testset "Euler with tetrahedral mesh" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] ) end - @trixi_testset "elixir_euler_tetrahedral_mesh_ec.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_tetrahedral_mesh_ec.jl"), - l2 = [0.10199177415993853, 0.11613427360212616, 0.11026702646784316, 0.10994524014778534, 0.2582449717237713], - linf = [0.2671818932369674, 0.2936313498471166, 0.34636540613352573, 0.2996048158961957, 0.7082318124804874] + @trixi_testset "Euler with tetrahedral mesh EC" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), + surface_integral = SurfaceIntegralWeakForm(flux_ranocha), + volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), + l2 = [0.014932088450136542, 0.017080219613061526, 0.016589517840793006, 0.015905000907070196, 0.03903416208587798], + linf = [0.06856547797256729, 0.08225664880340489, 0.06925055630951782, 0.06913016119820181, 0.19161418499621874] ) end - @trixi_testset "elixir_euler_hexahedral_mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_hexahedral_mesh.jl"), + @trixi_testset "Euler with hexahedral mesh" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), + element_type = Hex(), l2 = [0.00030580190715769566, 0.00040146357607439464, 0.00040146357607564597, 0.000401463576075708, 0.0015749412434154315], linf = [0.00036910287847780054, 0.00042659774184228283, 0.0004265977427213574, 0.00042659774250686233, 0.00143803344597071] ) From f09d5880c92def1f1546ee66ead4ea6cb6c496ba Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 12:19:40 -0500 Subject: [PATCH 47/58] renaming VX, ... -> vertex_coordinates_x, ... --- examples/dg_multi/elixir_euler_weakform_3d.jl | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/examples/dg_multi/elixir_euler_weakform_3d.jl b/examples/dg_multi/elixir_euler_weakform_3d.jl index ee05b28082e..3685698980e 100644 --- a/examples/dg_multi/elixir_euler_weakform_3d.jl +++ b/examples/dg_multi/elixir_euler_weakform_3d.jl @@ -14,8 +14,9 @@ source_terms = source_terms_convergence_test top_boundary(x, y, z, tol=50*eps()) = abs(y - 1) < tol rest_of_boundary(x, y, z, tol=50*eps()) = !top_boundary(x, y, z, tol) is_on_boundary = Dict(:top => top_boundary, :rest => rest_of_boundary) -VX, VY, VZ, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, 4) -mesh = VertexMappedMesh(VX, VY, VZ, EToV, dg, is_on_boundary = is_on_boundary) +vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, 4) +mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), EToV, + dg, is_on_boundary = is_on_boundary) boundary_condition_convergence_test = BoundaryConditionDirichlet(initial_condition) boundary_conditions = (; :top => boundary_condition_convergence_test, From ceb2585f0ed1507a8da02620374dcd09e6e4c02d Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 12:23:05 -0500 Subject: [PATCH 48/58] adding periodic 3d dgmulti elixir + tests --- .../elixir_euler_weakform_periodic_3d.jl | 34 +++++++++++++++++++ test/test_examples_dg_multi.jl | 15 ++++++++ 2 files changed, 49 insertions(+) create mode 100644 examples/dg_multi/elixir_euler_weakform_periodic_3d.jl diff --git a/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl b/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl new file mode 100644 index 00000000000..0d1eeeb08a1 --- /dev/null +++ b/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl @@ -0,0 +1,34 @@ +# !!! warning "Experimental features" + +using Trixi, OrdinaryDiffEq + +dg = DGMulti(; polydeg = 3, element_type = Tet(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) + +equations = CompressibleEulerEquations3D(1.4) +initial_condition = initial_condition_convergence_test +source_terms = source_terms_convergence_test + +vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV = StartUpDG.uniform_mesh(dg.basis.elementType, 4) +mesh = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), EToV, dg, + is_periodic = (true, true, true)) + +semi = SemidiscretizationHyperbolic(mesh, equations, initial_condition, dg, + source_terms = source_terms) + +tspan = (0.0, 0.1) +ode = semidiscretize(semi, tspan) + +summary_callback = SummaryCallback() +alive_callback = AliveCallback(alive_interval=10) +analysis_interval = 100 +analysis_callback = AnalysisCallback(semi, interval=analysis_interval, uEltype=real(dg)) +callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) + +############################################################################### +# run the simulation + +sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), + dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); +summary_callback() # print the timer summary diff --git a/test/test_examples_dg_multi.jl b/test/test_examples_dg_multi.jl index 75c7d9e7dc1..87a4a51dd87 100644 --- a/test/test_examples_dg_multi.jl +++ b/test/test_examples_dg_multi.jl @@ -100,6 +100,21 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end + @trixi_testset "Euler with tetrahedral mesh periodic" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_3d.jl"), + l2 = [0.0010317074322517949, 0.0012277090547035293, 0.0011273991123913515, 0.0010418496196130177, 0.004058878478404962], + linf = [0.003227752881827861, 0.005620317864620361, 0.0030514833972379307, 0.003987027618439498, 0.019282224709831652] + ) + end + + @trixi_testset "Euler with hexahedral mesh periodic" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_3d.jl"), + element_type = Hex(), + l2 = [0.00034230612468547436, 0.00044397204714598747, 0.0004439720471461567, 0.0004439720471464591, 0.0016639410646990126], + linf = [0.0003674374460325147, 0.0004253921341716982, 0.0004253921340786615, 0.0004253921340831024, 0.0014333414071048267] + ) + end + end end # module From 13b1d4861ac4b39c8f6f76b4e5f51a40cbc3e169 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Thu, 22 Jul 2021 13:32:15 -0500 Subject: [PATCH 49/58] renaming CI tests --- .github/workflows/ci.yml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 555135a89ff..acd976822e2 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -63,8 +63,7 @@ jobs: - 2d_part1 - 2d_part2 - 2d_part3 - - 2d_simplices - - 3d_simplices + - dg_multi - 2d_mpi - 2d_threaded - 3d_part1 From fda35fbb75118553d9d170fd2b47c1c16da4bd52 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 12:32:16 -0700 Subject: [PATCH 50/58] Apply suggestions from code review Co-authored-by: Michael Schlottke-Lakemper Co-authored-by: Hendrik Ranocha --- docs/src/meshes/mesh_data_meshes.md | 2 +- .../dg_multi/elixir_euler_triangulate_pkg_mesh.jl | 6 +++--- examples/dg_multi/elixir_euler_weakform_2d.jl | 6 +++--- examples/dg_multi/elixir_euler_weakform_3d.jl | 6 +++--- .../dg_multi/elixir_euler_weakform_periodic_2d.jl | 6 +++--- .../dg_multi/elixir_euler_weakform_periodic_3d.jl | 6 +++--- src/meshes/dg_multi_meshes.jl | 3 +-- src/solvers/dg_multi/flux_differencing.jl | 15 +++++++-------- 8 files changed, 24 insertions(+), 26 deletions(-) diff --git a/docs/src/meshes/mesh_data_meshes.md b/docs/src/meshes/mesh_data_meshes.md index 2be3e4d0755..6529cb7d412 100644 --- a/docs/src/meshes/mesh_data_meshes.md +++ b/docs/src/meshes/mesh_data_meshes.md @@ -115,7 +115,7 @@ approximation on a triangle. There are also several parameters which can be twea ## Trixi elixirs on simplicial and tensor product element meshes -Example elixirs on triangular, quadrilateral, tetrahedral, and simplicial meshes can be found in +Example elixirs with triangular, quadrilateral, and tetrahedral meshes can be found in the `examples/dg_multi` folder. Some key elixirs to look at: * `elixir_euler_weakform_2d.jl`: basic weak form DG discretization on a uniform triangular mesh. diff --git a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl index 0ab3261c70f..8f49248e650 100644 --- a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl @@ -3,9 +3,9 @@ using Triangulate using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, element_type = Tri(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) +dg = DGMulti(polydeg = 3, element_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/dg_multi/elixir_euler_weakform_2d.jl b/examples/dg_multi/elixir_euler_weakform_2d.jl index b9866e6b2f4..cf9cfec992a 100644 --- a/examples/dg_multi/elixir_euler_weakform_2d.jl +++ b/examples/dg_multi/elixir_euler_weakform_2d.jl @@ -2,9 +2,9 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, element_type = Tri(), approximation_type = Polynomial(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) +dg = DGMulti(polydeg = 3, element_type = Tri(), approximation_type = Polynomial(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/dg_multi/elixir_euler_weakform_3d.jl b/examples/dg_multi/elixir_euler_weakform_3d.jl index 3685698980e..91a719f05e3 100644 --- a/examples/dg_multi/elixir_euler_weakform_3d.jl +++ b/examples/dg_multi/elixir_euler_weakform_3d.jl @@ -2,9 +2,9 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, element_type = Tet(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) +dg = DGMulti(polydeg = 3, element_type = Tet(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl b/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl index f7b8dca25d2..50f786470fe 100644 --- a/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl +++ b/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl @@ -2,9 +2,9 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, element_type = Tri(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) +dg = DGMulti(polydeg = 3, element_type = Tri(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations2D(1.4) initial_condition = initial_condition_convergence_test diff --git a/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl b/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl index 0d1eeeb08a1..ad0d158df86 100644 --- a/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl +++ b/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl @@ -2,9 +2,9 @@ using Trixi, OrdinaryDiffEq -dg = DGMulti(; polydeg = 3, element_type = Tet(), - surface_integral = SurfaceIntegralWeakForm(FluxHLL()), - volume_integral = VolumeIntegralWeakForm()) +dg = DGMulti(polydeg = 3, element_type = Tet(), + surface_integral = SurfaceIntegralWeakForm(FluxHLL()), + volume_integral = VolumeIntegralWeakForm()) equations = CompressibleEulerEquations3D(1.4) initial_condition = initial_condition_convergence_test diff --git a/src/meshes/dg_multi_meshes.jl b/src/meshes/dg_multi_meshes.jl index ce24374f073..c9e48a00722 100644 --- a/src/meshes/dg_multi_meshes.jl +++ b/src/meshes/dg_multi_meshes.jl @@ -86,7 +86,7 @@ function VertexMappedMesh(triangulateIO, rd::RefElemData{2, Tri}, boundary_dict: end """ - VertexMappedMesh(triangulateIO, dg::DGMulti, boundary_dict::Dict{Symbol, Int}) + VertexMappedMesh(triangulateIO, dg::DGMulti, boundary_dict::Dict{Symbol, Int}) Constructor which uses `dg::DGMulti` instead of `rd::RefElemData`. """ @@ -98,4 +98,3 @@ VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, EToV, rd, args...; VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y), EToV, rd, args...; kwargs...) VertexMappedMesh(vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z, EToV, rd, args...; kwargs...) = VertexMappedMesh((vertex_coordinates_x, vertex_coordinates_y, vertex_coordinates_z), EToV, rd, args...; kwargs...) - diff --git a/src/solvers/dg_multi/flux_differencing.jl b/src/solvers/dg_multi/flux_differencing.jl index 6dfbb9ebcef..c23d629ba4b 100644 --- a/src/solvers/dg_multi/flux_differencing.jl +++ b/src/solvers/dg_multi/flux_differencing.jl @@ -13,7 +13,7 @@ Computes the flux difference ∑_j A[i, j] * f(u_i, u_j) and accumulates the res du_i = du[i] for j in rows if !skip_index(i,j) - du_i += ATr[j,i] * volume_flux(u_i, u[j]) + du_i = du_i + ATr[j,i] * volume_flux(u_i, u[j]) end end du[i] = du_i @@ -22,13 +22,13 @@ end # Version of function without `skip_index`, as mentioned in # https://github.com/trixi-framework/Trixi.jl/pull/695/files#r670403097 -@inline function hadamard_sum_A_transposed!(du, ATr, volume_flux::VF, u) where {VF} +@inline function hadamard_sum_A_transposed!(du, ATr, volume_flux, u) rows, cols = axes(ATr) for i in cols u_i = u[i] du_i = du[i] for j in rows - du_i += ATr[j,i] * volume_flux(u_i, u[j]) + du_i = du_i + ATr[j,i] * volume_flux(u_i, u[j]) end du[i] = du_i end @@ -38,7 +38,7 @@ end # combinations of reference differentiation operators scaled by geometric change of variables terms. # We use LazyArrays.jl for lazy evaluation of physical differentiation operators, so that we can # compute linear combinations of differentiation operators on-the-fly in an allocation-free manner. -function build_lazy_physical_derivative(element::Int, orientation::Int, +function build_lazy_physical_derivative(element, orientation, mesh::VertexMappedMesh{2, Tri}, dg, cache) @unpack Qrst_skew_Tr = cache @unpack rxJ, sxJ, ryJ, syJ = mesh.md @@ -50,7 +50,7 @@ function build_lazy_physical_derivative(element::Int, orientation::Int, end end -function build_lazy_physical_derivative(element::Int, orientation::Int, +function build_lazy_physical_derivative(element, orientation, mesh::VertexMappedMesh{3, Tet}, dg, cache) @unpack Qrst_skew_Tr = cache QrskewTr, QsskewTr, QtskewTr = Qrst_skew_Tr @@ -86,8 +86,7 @@ function calc_volume_integral!(du, u, volume_integral, end -function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, - RealT, uEltype) +function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:Polynomial}, RealT, uEltype) rd = dg.basis @unpack md = mesh @@ -126,7 +125,7 @@ function create_cache(mesh::VertexMappedMesh, equations, dg::DGMultiFluxDiff{<:P u_values, u_face_values, rhs_local_threaded, flux_face_values, local_values_threaded) end -function entropy_projection!(cache, u, mesh::VertexMappedMesh, equations, dg::DGMulti) +function entropy_projection!(cache, u, mesh::VertexMappedMesh, equations, dg::DGMulti) rd = dg.basis @unpack Vq = rd From 8177105ac5db106c3da52b10cb37853707740211 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:32:34 -0500 Subject: [PATCH 51/58] renaming dg_multi -> dgmulti --- .github/workflows/ci.yml | 2 +- docs/src/meshes/mesh_data_meshes.md | 8 ++++---- .../{analysis_dg_multi.jl => analysis_dgmulti.jl} | 0 src/solvers/{dg_multi => dgmulti}/flux_differencing.jl | 0 src/solvers/{dg_multi => dgmulti}/types_and_traits.jl | 0 5 files changed, 5 insertions(+), 5 deletions(-) rename src/callbacks_step/{analysis_dg_multi.jl => analysis_dgmulti.jl} (100%) rename src/solvers/{dg_multi => dgmulti}/flux_differencing.jl (100%) rename src/solvers/{dg_multi => dgmulti}/types_and_traits.jl (100%) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index acd976822e2..15d063c9469 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -63,7 +63,7 @@ jobs: - 2d_part1 - 2d_part2 - 2d_part3 - - dg_multi + - dgmulti - 2d_mpi - 2d_threaded - 3d_part1 diff --git a/docs/src/meshes/mesh_data_meshes.md b/docs/src/meshes/mesh_data_meshes.md index 6529cb7d412..d6d5c1cc8af 100644 --- a/docs/src/meshes/mesh_data_meshes.md +++ b/docs/src/meshes/mesh_data_meshes.md @@ -116,16 +116,16 @@ approximation on a triangle. There are also several parameters which can be twea ## Trixi elixirs on simplicial and tensor product element meshes Example elixirs with triangular, quadrilateral, and tetrahedral meshes can be found in -the `examples/dg_multi` folder. Some key elixirs to look at: +the `examples/dgmulti_2d` and `examples/dgmulti_3d` folders. Some key elixirs to look at: -* `elixir_euler_weakform_2d.jl`: basic weak form DG discretization on a uniform triangular mesh. +* `examples/dgmulti_2d/elixir_euler_weakform.jl`: basic weak form DG discretization on a uniform triangular mesh. Changing `element_type = Quad()` or `approximation_type = SBP()` will switch to a quadrilateral mesh or an SBP-type discretization. Changing `surface_integral = SurfaceIntegralWeakForm(flux_ec)` and `volume_integral = VolumeIntegralFluxDifferencing(flux_ec)` for some entropy conservative flux (e.g., `flux_chandrashekar` or `flux_ranocha`) will switch to an entropy conservative formulation. -* `elixir_euler_triangulate_pkg_mesh.jl`: uses a `TriangulateIO` unstructured mesh generated by +* `examples/dgmulti_2d/elixir_euler_triangulate_pkg_mesh.jl`: uses a `TriangulateIO` unstructured mesh generated by [Triangulate.jl](https://github.com/JuliaGeometry/Triangulate.jl). -* `elixir_euler_weakform_3d.jl`: basic weak form DG discretization on a uniform tetrahedral mesh. +* `examples/dgmulti_3d/elixir_euler_weakform.jl`: basic weak form DG discretization on a uniform tetrahedral mesh. Changing `element_type = Hex()` will switch to a hexahedral mesh. Changing `surface_integral = SurfaceIntegralWeakForm(flux_ec)` and `volume_integral = VolumeIntegralFluxDifferencing(flux_ec)` for some entropy conservative flux diff --git a/src/callbacks_step/analysis_dg_multi.jl b/src/callbacks_step/analysis_dgmulti.jl similarity index 100% rename from src/callbacks_step/analysis_dg_multi.jl rename to src/callbacks_step/analysis_dgmulti.jl diff --git a/src/solvers/dg_multi/flux_differencing.jl b/src/solvers/dgmulti/flux_differencing.jl similarity index 100% rename from src/solvers/dg_multi/flux_differencing.jl rename to src/solvers/dgmulti/flux_differencing.jl diff --git a/src/solvers/dg_multi/types_and_traits.jl b/src/solvers/dgmulti/types_and_traits.jl similarity index 100% rename from src/solvers/dg_multi/types_and_traits.jl rename to src/solvers/dgmulti/types_and_traits.jl From 7c8ea1ab263016c94d78c53ff587502b0f350926 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:33:08 -0500 Subject: [PATCH 52/58] more renaming - dg_multi -> dgmulti - estimate_dt(dg, mesh) -> estimate_dt(mesh, dg) --- .../elixir_euler_triangulate_pkg_mesh.jl | 2 +- .../elixir_euler_weakform.jl} | 2 +- .../elixir_euler_weakform_periodic.jl} | 2 +- .../elixir_euler_weakform.jl} | 2 +- .../elixir_euler_weakform_periodic.jl} | 2 +- src/solvers/{dg_multi => dgmulti}/dg.jl | 5 +++-- 6 files changed, 8 insertions(+), 7 deletions(-) rename examples/{dg_multi => dgmulti_2d}/elixir_euler_triangulate_pkg_mesh.jl (96%) rename examples/{dg_multi/elixir_euler_weakform_2d.jl => dgmulti_2d/elixir_euler_weakform.jl} (96%) rename examples/{dg_multi/elixir_euler_weakform_periodic_2d.jl => dgmulti_2d/elixir_euler_weakform_periodic.jl} (95%) rename examples/{dg_multi/elixir_euler_weakform_3d.jl => dgmulti_3d/elixir_euler_weakform.jl} (96%) rename examples/{dg_multi/elixir_euler_weakform_periodic_3d.jl => dgmulti_3d/elixir_euler_weakform_periodic.jl} (95%) rename src/solvers/{dg_multi => dgmulti}/dg.jl (98%) diff --git a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl b/examples/dgmulti_2d/elixir_euler_triangulate_pkg_mesh.jl similarity index 96% rename from examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl rename to examples/dgmulti_2d/elixir_euler_triangulate_pkg_mesh.jl index 8f49248e650..e4d394295dd 100644 --- a/examples/dg_multi/elixir_euler_triangulate_pkg_mesh.jl +++ b/examples/dgmulti_2d/elixir_euler_triangulate_pkg_mesh.jl @@ -40,5 +40,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) # run the simulation sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(mesh, dg), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_weakform_2d.jl b/examples/dgmulti_2d/elixir_euler_weakform.jl similarity index 96% rename from examples/dg_multi/elixir_euler_weakform_2d.jl rename to examples/dgmulti_2d/elixir_euler_weakform.jl index cf9cfec992a..fed3d66063a 100644 --- a/examples/dg_multi/elixir_euler_weakform_2d.jl +++ b/examples/dgmulti_2d/elixir_euler_weakform.jl @@ -40,5 +40,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) # run the simulation sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(mesh, dg), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl b/examples/dgmulti_2d/elixir_euler_weakform_periodic.jl similarity index 95% rename from examples/dg_multi/elixir_euler_weakform_periodic_2d.jl rename to examples/dgmulti_2d/elixir_euler_weakform_periodic.jl index 50f786470fe..10b23d7cc43 100644 --- a/examples/dg_multi/elixir_euler_weakform_periodic_2d.jl +++ b/examples/dgmulti_2d/elixir_euler_weakform_periodic.jl @@ -28,5 +28,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) # run the simulation sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(mesh, dg), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_weakform_3d.jl b/examples/dgmulti_3d/elixir_euler_weakform.jl similarity index 96% rename from examples/dg_multi/elixir_euler_weakform_3d.jl rename to examples/dgmulti_3d/elixir_euler_weakform.jl index 91a719f05e3..44ba2f8cd9e 100644 --- a/examples/dg_multi/elixir_euler_weakform_3d.jl +++ b/examples/dgmulti_3d/elixir_euler_weakform.jl @@ -39,5 +39,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) # run the simulation sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(mesh, dg), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl b/examples/dgmulti_3d/elixir_euler_weakform_periodic.jl similarity index 95% rename from examples/dg_multi/elixir_euler_weakform_periodic_3d.jl rename to examples/dgmulti_3d/elixir_euler_weakform_periodic.jl index ad0d158df86..dc5c413ceac 100644 --- a/examples/dg_multi/elixir_euler_weakform_periodic_3d.jl +++ b/examples/dgmulti_3d/elixir_euler_weakform_periodic.jl @@ -30,5 +30,5 @@ callbacks = CallbackSet(summary_callback, alive_callback, analysis_callback) # run the simulation sol = solve(ode, CarpenterKennedy2N54(williamson_condition=false), - dt = 0.5 * estimate_dt(dg, mesh), save_everystep=false, callback=callbacks); + dt = 0.5 * estimate_dt(mesh, dg), save_everystep=false, callback=callbacks); summary_callback() # print the timer summary diff --git a/src/solvers/dg_multi/dg.jl b/src/solvers/dgmulti/dg.jl similarity index 98% rename from src/solvers/dg_multi/dg.jl rename to src/solvers/dgmulti/dg.jl index 1fb8dcb64f8..48a464a624a 100644 --- a/src/solvers/dg_multi/dg.jl +++ b/src/solvers/dgmulti/dg.jl @@ -57,17 +57,18 @@ function compute_coefficients!(u::StructArray, initial_condition, t, rd = dg.basis @unpack u_values = cache + # evaluate the initial condition at quadrature points @threaded for i in each_quad_node_global(mesh, dg, cache) u_values[i] = initial_condition(getindex.(md.xyzq, i), t, equations) end - # compute L2 projection + # multiplying by Pq computes the L2 projection StructArrays.foreachfield(mul_by!(rd.Pq), u, u_values) end # estimates the timestep based on polynomial degree and mesh. Does not account for physics (e.g., # computes an estimate of `dt` based on the advection equation with constant unit advection speed). -function estimate_dt(dg::DGMulti, mesh::AbstractMeshData) +function estimate_dt(mesh::AbstractMeshData, dg::DGMulti) rd = dg.basis # RefElemData return StartUpDG.estimate_h(rd, mesh.md) / StartUpDG.inverse_trace_constant(rd) end From 361f2f505ba5e674df9ee7cd0d3d3e08d69fce20 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:34:04 -0500 Subject: [PATCH 53/58] fix indentation in docstring --- src/meshes/{dg_multi_meshes.jl => dgmulti_meshes.jl} | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) rename src/meshes/{dg_multi_meshes.jl => dgmulti_meshes.jl} (98%) diff --git a/src/meshes/dg_multi_meshes.jl b/src/meshes/dgmulti_meshes.jl similarity index 98% rename from src/meshes/dg_multi_meshes.jl rename to src/meshes/dgmulti_meshes.jl index c9e48a00722..931933f885f 100644 --- a/src/meshes/dg_multi_meshes.jl +++ b/src/meshes/dgmulti_meshes.jl @@ -45,7 +45,7 @@ end - `vertex_coordinates` is a tuple of vectors containing x,y,... components of the vertex coordinates - `EToV` is a 2D array containing element-to-vertex connectivities for each element - `rd` is a `RefElemData` from `StartUpDG.jl`, and contains information associated with to the -reference element (e.g., quadrature, basis evaluation, differentiation, etc). + reference element (e.g., quadrature, basis evaluation, differentiation, etc). - `is_on_boundary` specifies boundary using a `Dict{Symbol, <:Function}` - `is_periodic` is a tuple of booleans specifying periodicity = `true`/`false` in the (x,y,z) direction. """ From a57870e13fd978f31bb0644f321992d63d534e07 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:34:19 -0500 Subject: [PATCH 54/58] renaming dg_multi -> dgmulti in tests --- test/runtests.jl | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/test/runtests.jl b/test/runtests.jl index dd4aaf3b80c..9c93a2e7077 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -50,8 +50,8 @@ const TRIXI_NTHREADS = clamp(Sys.CPU_THREADS, 2, 3) include("test_examples_2d_part3.jl") end - @time if TRIXI_TEST == "all" || TRIXI_TEST == "dg_multi" - include("test_examples_dg_multi.jl") + @time if TRIXI_TEST == "all" || TRIXI_TEST == "dgmulti" + include("test_examples_dgmulti.jl") end @time if TRIXI_TEST == "all" || TRIXI_TEST == "3d_part1" From c01f6c508f05e2720b00c00efd2567153bbd3948 Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:35:39 -0500 Subject: [PATCH 55/58] separating dgmulti elixirs into 2d/3d --- ...s_dg_multi.jl => test_examples_dgmulti.jl} | 59 ++++++++++--------- 1 file changed, 32 insertions(+), 27 deletions(-) rename test/{test_examples_dg_multi.jl => test_examples_dgmulti.jl} (80%) diff --git a/test/test_examples_dg_multi.jl b/test/test_examples_dgmulti.jl similarity index 80% rename from test/test_examples_dg_multi.jl rename to test/test_examples_dgmulti.jl index 87a4a51dd87..a851ce56e26 100644 --- a/test/test_examples_dg_multi.jl +++ b/test/test_examples_dgmulti.jl @@ -6,19 +6,19 @@ using Trixi include("test_trixi.jl") # pathof(Trixi) returns /path/to/Trixi/src/Trixi.jl, dirname gives the parent directory -EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_multi") +EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dgmulti_2d") -@testset "DGMulti" begin - @trixi_testset "Euler triangular mesh" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), +@testset "DGMulti 2D" begin + @trixi_testset "elixir_euler_weakform.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), cells_per_dimension = (4,4), l2 = [0.0013463253573454783, 0.0014235911638070984, 0.0014235911638076622, 0.004721923810347086], linf = [0.0015248269221803668, 0.002070690855385582, 0.002070690855385804, 0.004913338290754687] ) end - @trixi_testset "Euler triangular mesh SBP" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + @trixi_testset "elixir_euler_weakform.jl (SBP)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), cells_per_dimension = (4,4), approximation_type = SBP(), l2 = [0.007465048853079056, 0.005297478943323888, 0.005297478943334149, 0.014701766352428895], @@ -26,8 +26,8 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - @trixi_testset "Euler quadrilateral mesh.jl" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + @trixi_testset "elixir_euler_weakform.jl (Quadrilateral elements)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), cells_per_dimension = (4,4), element_type = Quad(), l2 = [0.0002909691660845978, 0.0002811425883546657, 0.0002811425883549579, 0.0010200600240538172], @@ -35,8 +35,8 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - @trixi_testset "Euler triangular mesh EC" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + @trixi_testset "elixir_euler_weakform.jl (EC) " begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), cells_per_dimension = (4,4), volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), surface_integral = SurfaceIntegralWeakForm(flux_ranocha), @@ -45,8 +45,8 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - @trixi_testset "Euler triangular mesh SBP EC" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), + @trixi_testset "elixir_euler_weakform.jl (SBP, EC)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), cells_per_dimension = (4,4), volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), surface_integral = SurfaceIntegralWeakForm(flux_ranocha), @@ -56,35 +56,40 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - @trixi_testset "Euler triangular mesh convergence" begin - mean_convergence = convergence_test(@__MODULE__, joinpath(EXAMPLES_DIR, "elixir_euler_weakform_2d.jl"), 2) + @trixi_testset "elixir_euler_weakform.jl (convergence)" begin + mean_convergence = convergence_test(@__MODULE__, joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), 2) @test isapprox(mean_convergence[:l2], [4.2498632232077815, 4.133717042428824, 4.133717042041395, 4.086223177072245], rtol=0.05) end - @trixi_testset "Euler periodic triangular mesh" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_2d.jl"), + @trixi_testset "elixir_euler_weakform_periodic.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic.jl"), l2 = [0.0014986508075708323, 0.001528523420746786, 0.0015285234207473158, 0.004846505183839211], linf = [0.0015062108658376872, 0.0019373508504645365, 0.0019373508504538783, 0.004742686826709086] ) end - @trixi_testset "Euler with Triangulate.jl mesh" begin + @trixi_testset "elixir_euler_triangulate_pkg_mesh.jl" begin @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_triangulate_pkg_mesh.jl"), l2 = [0.00015405739868423074, 0.00014530283464035389, 0.00014870936695617315, 0.00044410650633679334], linf = [0.00039269979059053384, 0.0004237090504681795, 0.000577877861525522, 0.0015066603278119928] ) end +end + +EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dgmulti_3d") + +@testset "DGMulti 3D" begin # 3d tet/hex tests - @trixi_testset "Euler with tetrahedral mesh" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), + @trixi_testset "elixir_euler_weakform.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), l2 = [0.0010029534292051608, 0.0011682205957721673, 0.001072975385793516, 0.000997247778892257, 0.0039364354651358294], linf = [0.003660737033303718, 0.005625620600749226, 0.0030566354814669516, 0.0041580358824311325, 0.019326660236036464] ) end - @trixi_testset "Euler with tetrahedral mesh EC" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), + @trixi_testset "elixir_euler_weakform.jl (EC)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), surface_integral = SurfaceIntegralWeakForm(flux_ranocha), volume_integral = VolumeIntegralFluxDifferencing(flux_ranocha), l2 = [0.014932088450136542, 0.017080219613061526, 0.016589517840793006, 0.015905000907070196, 0.03903416208587798], @@ -92,23 +97,23 @@ EXAMPLES_DIR = joinpath(pathof(Trixi) |> dirname |> dirname, "examples", "dg_mul ) end - @trixi_testset "Euler with hexahedral mesh" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_3d.jl"), + @trixi_testset "elixir_euler_weakform.jl (Hexahedral elements)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform.jl"), element_type = Hex(), l2 = [0.00030580190715769566, 0.00040146357607439464, 0.00040146357607564597, 0.000401463576075708, 0.0015749412434154315], linf = [0.00036910287847780054, 0.00042659774184228283, 0.0004265977427213574, 0.00042659774250686233, 0.00143803344597071] ) end - @trixi_testset "Euler with tetrahedral mesh periodic" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_3d.jl"), + @trixi_testset "elixir_euler_weakform_periodic.jl" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic.jl"), l2 = [0.0010317074322517949, 0.0012277090547035293, 0.0011273991123913515, 0.0010418496196130177, 0.004058878478404962], linf = [0.003227752881827861, 0.005620317864620361, 0.0030514833972379307, 0.003987027618439498, 0.019282224709831652] ) end - @trixi_testset "Euler with hexahedral mesh periodic" begin - @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic_3d.jl"), + @trixi_testset "elixir_euler_weakform_periodic.jl (Hexahedral elements)" begin + @test_trixi_include(joinpath(EXAMPLES_DIR, "elixir_euler_weakform_periodic.jl"), element_type = Hex(), l2 = [0.00034230612468547436, 0.00044397204714598747, 0.0004439720471461567, 0.0004439720471464591, 0.0016639410646990126], linf = [0.0003674374460325147, 0.0004253921341716982, 0.0004253921340786615, 0.0004253921340831024, 0.0014333414071048267] From 0a37f8b98c6ed7c5d670b22271c22f85b327bfad Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:35:54 -0500 Subject: [PATCH 56/58] selectively importing/exporting from StartUpDG --- src/Trixi.jl | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/src/Trixi.jl b/src/Trixi.jl index a9375ddf268..0cb9beefce1 100644 --- a/src/Trixi.jl +++ b/src/Trixi.jl @@ -195,18 +195,17 @@ export trixi_include, examples_dir, get_examples, default_example, default_examp export convergence_test, jacobian_fd, jacobian_ad_forward, linear_structure # DGMulti solvers -using StartUpDG -@reexport using StartUpDG: StartUpDG, RefElemData, MeshData, Polynomial, SBP -@reexport using StartUpDG: Line, Tri, Quad, Hex, Tet, AbstractElemShape +@reexport using StartUpDG: StartUpDG, Polynomial, SBP, Line, Tri, Quad, Hex, Tet +using StartUpDG: RefElemData, MeshData, AbstractElemShape -include("solvers/dg_multi/types_and_traits.jl") +include("solvers/dgmulti/types_and_traits.jl") export DGMulti -include("meshes/dg_multi_meshes.jl") +include("meshes/dgmulti_meshes.jl") export AbstractMeshData, VertexMappedMesh -include("solvers/dg_multi/dg.jl") +include("solvers/dgmulti/dg.jl") export estimate_dt -include("solvers/dg_multi/flux_differencing.jl") -include("callbacks_step/analysis_dg_multi.jl") +include("solvers/dgmulti/flux_differencing.jl") +include("callbacks_step/analysis_dgmulti.jl") # Visualization-related exports export PlotData1D, PlotData2D, getmesh, adapt_to_mesh_level!, adapt_to_mesh_level From 827379e84b05d4ab121675eabcf1066af23e232e Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 17:36:01 -0500 Subject: [PATCH 57/58] adding compat bounds for StartUpDG --- Project.toml | 1 + 1 file changed, 1 insertion(+) diff --git a/Project.toml b/Project.toml index 8ec6da5aac7..9104ef569c3 100644 --- a/Project.toml +++ b/Project.toml @@ -48,6 +48,7 @@ RecipesBase = "1.1" Reexport = "1.0" Requires = "1.1" StaticArrays = "1.0" +StartUpDG = "0.10.2" StrideArrays = "0.1.11" StructArrays = "0.6" SummationByPartsOperators = "0.5.4" From c7122fa3cc280b4c4f923c8751074c067be2a3ff Mon Sep 17 00:00:00 2001 From: Jesse Chan Date: Fri, 23 Jul 2021 18:01:59 -0500 Subject: [PATCH 58/58] adding kwarg option for DGMulti passed onto RefElemData --- src/solvers/dgmulti/types_and_traits.jl | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/solvers/dgmulti/types_and_traits.jl b/src/solvers/dgmulti/types_and_traits.jl index 6d8eda4e524..5e80773b69c 100644 --- a/src/solvers/dgmulti/types_and_traits.jl +++ b/src/solvers/dgmulti/types_and_traits.jl @@ -15,7 +15,8 @@ Base.real(rd::RefElemData{NDIMS, Elem, ApproxType, Nfaces, RealT}) where {NDIMS, approximation_type=Polynomial(), surface_flux=flux_central, surface_integral=SurfaceIntegralWeakForm(surface_flux), - volume_integral=VolumeIntegralWeakForm()) + volume_integral=VolumeIntegralWeakForm(), + RefElemData_kwargs...) Create a discontinuous Galerkin method which uses - approximations of polynomial degree `polydeg` @@ -24,14 +25,17 @@ Create a discontinuous Galerkin method which uses Optional: - `approximation_type` (default is `Polynomial()`; `SBP()` also supported for `Tri()`, `Quad()`, and `Hex()` element types). +- `RefElemData_kwargs` are additional keyword arguments for `RefElemData`, such as `quad_rule_vol`. + For more info, see the [StartUpDG.jl docs](https://jlchan.github.io/StartUpDG.jl/dev/). """ function DGMulti(; polydeg::Integer, element_type::AbstractElemShape, approximation_type=Polynomial(), surface_flux=flux_central, surface_integral=SurfaceIntegralWeakForm(surface_flux), - volume_integral=VolumeIntegralWeakForm()) - rd = RefElemData(element_type, approximation_type, polydeg) + volume_integral=VolumeIntegralWeakForm(), + kwargs...) + rd = RefElemData(element_type, approximation_type, polydeg, kwargs...) return DG(rd, nothing #= mortar =#, surface_integral, volume_integral) end