• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

trixi-framework / Trixi.jl / 21639639306

03 Feb 2026 05:01PM UTC coverage: 14.281% (-82.8%) from 97.034%
21639639306

Pull #2601

github

web-flow
Merge fd2e0cdf8 into ead0db32a
Pull Request #2601: Adaptive Volume Integral

28 of 281 new or added lines in 41 files covered. (9.96%)

36284 existing lines in 548 files now uncovered.

6317 of 44235 relevant lines covered (14.28%)

100377.05 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.0
/src/solvers/dgsem_tree/subcell_finite_volume_O2.jl
1
"""
2
    reconstruction_constant(u_ll, u_lr, u_rl, u_rr,
3
                            sc_interface_coords,
4
                            node_index, limiter, dg)
5

6
Returns the constant "reconstructed" values `u_lr, u_rl` at the interface `sc_interface_coords[node_index - 1]`.
7
Supposed to be used in conjunction with [`VolumeIntegralPureLGLFiniteVolumeO2`](@ref).
8
Formally first order accurate.
9
If a first-order finite volume scheme is desired, [`VolumeIntegralPureLGLFiniteVolume`](@ref) is an
10
equivalent, but more efficient choice.
11
"""
UNCOV
12
@inline function reconstruction_constant(u_ll, u_lr, u_rl, u_rr,
×
13
                                         sc_interface_coords, node_index,
14
                                         limiter, dg)
UNCOV
15
    return u_lr, u_rl
×
16
end
17

18
# Helper functions for reconstructions below
UNCOV
19
@inline function reconstruction_linear(u_lr, u_rl, s_l, s_r,
×
20
                                       x_lr, x_rl, sc_interface_coords, node_index)
21
    # Linear reconstruction at the interface
UNCOV
22
    u_lr = u_lr + s_l * (sc_interface_coords[node_index - 1] - x_lr)
×
UNCOV
23
    u_rl = u_rl + s_r * (sc_interface_coords[node_index - 1] - x_rl)
×
24

UNCOV
25
    return u_lr, u_rl
×
26
end
27

28
#             Reference element:             
29
#  -1 ------------------0------------------ 1 -> x
30
# Gauss-Lobatto-Legendre nodes (schematic for k = 3):
31
#   .          .                  .         .
32
#   ^          ^                  ^         ^
33
# Node indices:
34
#   1          2                  3         4
35
# The inner subcell boundaries are governed by the
36
# cumulative sum of the quadrature weights - 1 .
37
#  -1 ------------------0------------------ 1 -> x
38
#        w1-1      (w1+w2)-1   (w1+w2+w3)-1
39
#   |     |             |             |     |
40
# Note that only the inner boundaries are stored.
41
# Subcell interface indices, loop only over 2 -> nnodes(dg) = 4
42
#   1     2             3             4     5
43
#
44
# In general a four-point stencil is required, since we reconstruct the
45
# piecewise linear solution in both subcells next to the subcell interface.
46
# Since these subcell boundaries are not aligned with the DG nodes,
47
# on each neighboring subcell two linear solutions are reconstructed => 4 point stencil.
48
# For the outer interfaces the stencil shrinks since we do not consider values 
49
# outside the element (volume integral).
50
# 
51
# The left subcell node values are labelled `_ll` (left-left) and `_lr` (left-right), while
52
# the right subcell node values are labelled `_rl` (right-left) and `_rr` (right-right).
53

54
"""
55
    reconstruction_O2_full(u_ll, u_lr, u_rl, u_rr,
56
                           sc_interface_coords, node_index,
57
                           limiter, dg::DGSEM)
58

59
Returns the reconstructed values `u_lr, u_rl` at the interface `sc_interface_coords[node_index - 1]`.
60
Computes limited (linear) slopes on the subcells for a DGSEM element.
61
Supposed to be used in conjunction with [`VolumeIntegralPureLGLFiniteVolumeO2`](@ref).
62

63
The supplied `limiter` governs the choice of slopes given the nodal values
64
`u_ll`, `u_lr`, `u_rl`, and `u_rr` at the (Gauss-Lobatto Legendre) nodes.
65

66
**Symmetric ** total-Variation-Diminishing (TVD) choices for the limiter are
67
    1) [`minmod`](@ref)
68
    2) [`monotonized_central`](@ref)
69
    3) [`superbee`](@ref)
70
    4) [`vanleer`](@ref)
71
    5) [`koren_symmetric`](@ref)
72
**Asymmetric** limiters are also available, e.g.,
73
    1) [`koren`](@ref) for positive (right-going) velocities
74
    2) [`koren_flipped`](@ref) for negative (left-going) velocities
75

76
The reconstructed slopes are for `reconstruction_O2_full` not limited at the cell boundaries.
77
Formally second order accurate when used without a limiter, i.e., `limiter = `[`central_slope`](@ref).
78
This approach corresponds to equation (79) described in
79
- Rueda-Ramírez, Hennemann, Hindenlang, Winters, & Gassner (2021).
80
  "An entropy stable nodal discontinuous Galerkin method for the resistive MHD equations.
81
   Part II: Subcell finite volume shock capturing"
82
  [JCP: 2021.110580](https://doi.org/10.1016/j.jcp.2021.110580)
83
"""
UNCOV
84
@inline function reconstruction_O2_full(u_ll, u_lr, u_rl, u_rr,
×
85
                                        sc_interface_coords, node_index,
86
                                        limiter, dg::DGSEM)
UNCOV
87
    @unpack nodes = dg.basis
×
UNCOV
88
    x_lr = nodes[node_index - 1]
×
UNCOV
89
    x_rl = nodes[node_index]
×
90

91
    # Slope between "middle" nodes
UNCOV
92
    s_m = (u_rl - u_lr) / (x_rl - x_lr)
×
93

UNCOV
94
    if node_index == 2 # Catch case ll == lr
×
UNCOV
95
        s_l = s_m # Use unlimited "central" slope
×
96
    else
UNCOV
97
        x_ll = nodes[node_index - 2]
×
98
        # Slope between "left" nodes
UNCOV
99
        s_lr = (u_lr - u_ll) / (x_lr - x_ll)
×
100
        # Select slope between extrapolated (left) and crossing (middle) slope
UNCOV
101
        s_l = limiter.(s_lr, s_m)
×
102
    end
103

UNCOV
104
    if node_index == nnodes(dg) # Catch case rl == rr
×
UNCOV
105
        s_r = s_m # Use unlimited "central" slope
×
106
    else
UNCOV
107
        x_rr = nodes[node_index + 1]
×
108
        # Slope between "right" nodes
UNCOV
109
        s_rl = (u_rr - u_rl) / (x_rr - x_rl)
×
110
        # Select slope between crossing (middle) and extrapolated (right) slope
UNCOV
111
        s_r = limiter.(s_m, s_rl)
×
112
    end
113

UNCOV
114
    return reconstruction_linear(u_lr, u_rl, s_l, s_r,
×
115
                                 x_lr, x_rl, sc_interface_coords, node_index)
116
end
117

118
"""
119
    reconstruction_O2_inner(u_ll, u_lr, u_rl, u_rr,
120
                            sc_interface_coords, node_index,
121
                            limiter, dg::DGSEM)
122

123
Returns the reconstructed values `u_lr, u_rl` at the interface `sc_interface_coords[node_index - 1]`.
124
Computes limited (linear) slopes on the *inner* subcells for a DGSEM element.
125
Supposed to be used in conjunction with [`VolumeIntegralPureLGLFiniteVolumeO2`](@ref).
126

127
The supplied `limiter` governs the choice of slopes given the nodal values
128
`u_ll`, `u_lr`, `u_rl`, and `u_rr` at the (Gauss-Lobatto Legendre) nodes.
129

130
**Symmetric ** total-Variation-Diminishing (TVD) choices for the limiter are
131
    1) [`minmod`](@ref)
132
    2) [`monotonized_central`](@ref)
133
    3) [`superbee`](@ref)
134
    4) [`vanleer`](@ref)
135
    5) [`koren_symmetric`](@ref)
136
**Asymmetric** limiters are also available, e.g.,
137
    1) [`koren`](@ref) for dominantly positive velocities
138
    2) [`koren_flipped`](@ref) for dominantly negative velocities
139

140
For the outer, i.e., boundary subcells, constant values are used, i.e, no reconstruction.
141
This reduces the order of the scheme below 2.
142
This approach corresponds to equation (78) described in
143
- Rueda-Ramírez, Hennemann, Hindenlang, Winters, & Gassner (2021).
144
  "An entropy stable nodal discontinuous Galerkin method for the resistive MHD equations. 
145
   Part II: Subcell finite volume shock capturing"
146
  [JCP: 2021.110580](https://doi.org/10.1016/j.jcp.2021.110580)
147
"""
UNCOV
148
@inline function reconstruction_O2_inner(u_ll, u_lr, u_rl, u_rr,
×
149
                                         sc_interface_coords, node_index,
150
                                         limiter, dg::DGSEM)
UNCOV
151
    @unpack nodes = dg.basis
×
UNCOV
152
    x_lr = nodes[node_index - 1]
×
UNCOV
153
    x_rl = nodes[node_index]
×
154

155
    # Slope between "middle" nodes
UNCOV
156
    s_m = (u_rl - u_lr) / (x_rl - x_lr)
×
157

UNCOV
158
    if node_index == 2 # Catch case ll == lr
×
159
        # Do not reconstruct at the boundary
UNCOV
160
        s_l = zero(s_m)
×
161
    else
UNCOV
162
        x_ll = nodes[node_index - 2]
×
163
        # Slope between "left" nodes
UNCOV
164
        s_lr = (u_lr - u_ll) / (x_lr - x_ll)
×
165
        # Select slope between extrapolated (left) and crossing (middle) slope
UNCOV
166
        s_l = limiter.(s_lr, s_m)
×
167
    end
168

UNCOV
169
    if node_index == nnodes(dg) # Catch case rl == rr
×
170
        # Do not reconstruct at the boundary
UNCOV
171
        s_r = zero(s_m)
×
172
    else
UNCOV
173
        x_rr = nodes[node_index + 1]
×
174
        # Slope between "right" nodes
UNCOV
175
        s_rl = (u_rr - u_rl) / (x_rr - x_rl)
×
176
        # Select slope between crossing (middle) and extrapolated (right) slope
UNCOV
177
        s_r = limiter.(s_m, s_rl)
×
178
    end
179

UNCOV
180
    return reconstruction_linear(u_lr, u_rl, s_l, s_r,
×
181
                                 x_lr, x_rl, sc_interface_coords, node_index)
182
end
183

184
"""
185
    central_slope(sl, sr)
186

187
Central, non-TVD reconstruction given left and right slopes `sl` and `sr`.
188
Gives formally full order of accuracy at the expense of sacrificed nonlinear stability.
189
Similar in spirit to [`flux_central`](@ref).
190
"""
UNCOV
191
@inline function central_slope(sl, sr)
×
UNCOV
192
    return 0.5f0 * (sl + sr)
×
193
end
194

195
"""
196
    minmod(sl, sr)
197

198
Classic minmod limiter function for a TVD reconstruction given left and right slopes `sl` and `sr`.
199
There are many different ways how the minmod limiter can be implemented.
200
For reference, see for instance Eq. (6.27) in
201

202
- Randall J. LeVeque (2002)
203
  Finite Volume Methods for Hyperbolic Problems
204
  [DOI: 10.1017/CBO9780511791253](https://doi.org/10.1017/CBO9780511791253)
205
"""
UNCOV
206
@inline function minmod(sl, sr)
×
UNCOV
207
    return 0.5f0 * (sign(sl) + sign(sr)) * min(abs(sl), abs(sr))
×
208
end
209

210
"""
211
    monotonized_central(sl, sr)
212

213
Monotonized central limiter function for a TVD reconstruction given left and right slopes `sl` and `sr`.
214
There are many different ways how the monotonized central limiter can be implemented.
215
For reference, see for instance Eq. (6.29) in
216

217
- Randall J. LeVeque (2002)
218
  Finite Volume Methods for Hyperbolic Problems
219
  [DOI: 10.1017/CBO9780511791253](https://doi.org/10.1017/CBO9780511791253)
220
"""
UNCOV
221
@inline function monotonized_central(sl, sr)
×
222
    # Use recursive property of minmod function
UNCOV
223
    return minmod(0.5f0 * (sl + sr), 2 * minmod(sl, sr))
×
224
end
225

226
"""
227
    superbee(sl, sr)
228

229
Superbee limiter function for a TVD reconstruction given left and right slopes `sl` and `sr`.
230
There are many different ways how the superbee limiter can be implemented.
231
For reference, see for instance Eq. (6.28) in
232

233
- Randall J. LeVeque (2002)
234
  Finite Volume Methods for Hyperbolic Problems
235
  [DOI: 10.1017/CBO9780511791253](https://doi.org/10.1017/CBO9780511791253)
236
"""
UNCOV
237
@inline function superbee(sl, sr)
×
UNCOV
238
    return maxmod(minmod(sl, 2 * sr), minmod(2 * sl, sr))
×
239
end
240

241
"""
242
    vanleer(sl, sr)
243

244
Symmetric limiter by van Leer.
245
See for reference page 70 in 
246

247
- Siddhartha Mishra, Ulrik Skre Fjordholm and Rémi Abgrall
248
  Numerical methods for conservation laws and related equations.
249
  [Link](https://metaphor.ethz.ch/x/2019/hs/401-4671-00L/literature/mishra_hyperbolic_pdes.pdf)
250
"""
UNCOV
251
@inline function vanleer(sl, sr)
×
UNCOV
252
    if abs(sl) + abs(sr) > zero(sl)
×
UNCOV
253
        return (abs(sr) * sl + abs(sl) * sr) / (abs(sl) + abs(sr))
×
254
    else
UNCOV
255
        return zero(sl)
×
256
    end
257
end
258

259
"""
260
    koren(sl, sr)
261

262
**Asymmetric** limiter by Barry Koren, originally proposed in Chapter 5.2.2. of
263

264
- B. Koren (1993)
265
  A robust upwind discretization method for advection, diffusion and source terms.
266
  In: C.B. Vreugdenhil, B. Koren (eds): Numerical Methods for Advection-Diffusion Problems.
267
  Notes on Numerical Fluid Mechanics, Vol 15. Braunschweig/Wiesbaden.
268
  [URL](https://ir.cwi.nl/pub/2269/2269D.pdf)
269

270
A version in left/right slopes `sl, sr` is given by equations (14) and (15) in
271
- P. Jenny (2020)
272
  Time adaptive conservative finite volume method.
273
  [DOI:10.1016/j.jcp.2019.109067](https://doi.org/10.1016/j.jcp.2019.109067)
274

275
This limiter is biased for positive (right-going) velocities.
276
For the flipped version, which is biased for negative (left-going) velocities,
277
see [`koren_flipped`](@ref).
278
"""
UNCOV
279
@inline function koren(sl, sr)
×
UNCOV
280
    return minmod(2 * minmod(sl, sr), (sl + 2 * sr) / 3)
×
281
end
282

283
"""
284
    koren_flipped(sl, sr)
285

286
**Asymmetric** limiter by Barry Koren, flipped version biased for negative (left-going) velocities.
287
See [`koren`](@ref) for references.
288
"""
UNCOV
289
@inline function koren_flipped(sl, sr)
×
UNCOV
290
    return koren(sr, sl)
×
291
end
292

293
"""
294
    koren_symmetric(sl, sr)
295

296
**Symmetric** version of the [`koren`](@ref) limiter by Barry Koren.
297
Puts equal weight on left and right slopes.
298
"""
UNCOV
299
@inline function koren_symmetric(sl, sr)
×
UNCOV
300
    return minmod(2 * minmod(sl, sr), minmod(sl + 2 * sr, 2 * sl + sr) / 3)
×
301
end
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc