Skip to content

Commit 55df592

Browse files
authored
Merge pull request #31213 from anshchaube/chtbc
Conjugate heat transfer for segregated solvers in MOOSE-NS
2 parents dfd9bde + 18103cb commit 55df592

38 files changed

+2128
-39
lines changed

framework/include/base/MooseFunctorArguments.h

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -255,6 +255,15 @@ struct NodeArg
255255
/// Functors may still be able to evaluate a NodeArg with this as the provided \p subdomain_ids
256256
/// if the functor has no "sidedness", e.g. like a H1 finite element family variable
257257
static const std::set<SubdomainID> undefined_subdomain_connection;
258+
259+
/**
260+
* Friend function that allows this structure to be used as keys in ordered containers like sets
261+
* and maps
262+
*/
263+
friend bool operator<(const NodeArg & l, const NodeArg & r)
264+
{
265+
return std::make_tuple(l.node, l.subdomain_ids) < std::make_tuple(r.node, r.subdomain_ids);
266+
}
258267
};
259268

260269
/**
@@ -283,5 +292,15 @@ struct ElemQpArg
283292
* @returns The conceptual physical location of this data structure
284293
*/
285294
libMesh::Point getPoint() const { return point; }
295+
296+
/**
297+
* Friend function that allows this structure to be used as keys in ordered containers like sets
298+
* and maps
299+
*/
300+
friend bool operator<(const ElemQpArg & l, const ElemQpArg & r)
301+
{
302+
return std::make_tuple(l.elem, l.qp, l.qrule, l.point) <
303+
std::make_tuple(r.elem, r.qp, r.qrule, r.point);
304+
}
286305
};
287306
}

framework/include/linearfvkernels/LinearFVFluxKernel.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,11 @@ class LinearFVFluxKernel : public LinearFVKernel, public FaceArgProducerInterfac
6969
*/
7070
virtual Real computeBoundaryRHSContribution(const LinearFVBoundaryCondition & bc) = 0;
7171

72+
/**
73+
* Computes the flux from this kernel on a boundary
74+
*/
75+
virtual Real computeBoundaryFlux(const LinearFVBoundaryCondition & bc);
76+
7277
protected:
7378
/**
7479
* Determine the single sided face argument when evaluating a functor on a face.

framework/src/linearfvbcs/LinearFVBoundaryCondition.C

Lines changed: 4 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -96,13 +96,8 @@ LinearFVBoundaryCondition::computeCellToFaceDistance() const
9696
RealVectorValue
9797
LinearFVBoundaryCondition::computeCellToFaceVector() const
9898
{
99-
const auto is_on_mesh_boundary = !_current_face_info->neighborPtr();
100-
const auto defined_on_elem =
101-
is_on_mesh_boundary ? true : (_current_face_type == FaceInfo::VarFaceNeighbors::ELEM);
102-
if (is_on_mesh_boundary)
103-
return _current_face_info->dCN();
104-
else
105-
return (_current_face_info->faceCentroid() - (defined_on_elem
106-
? _current_face_info->elemCentroid()
107-
: _current_face_info->neighborCentroid()));
99+
const auto defined_on_elem = _current_face_type == FaceInfo::VarFaceNeighbors::ELEM;
100+
return (_current_face_info->faceCentroid() - (defined_on_elem
101+
? _current_face_info->elemCentroid()
102+
: _current_face_info->neighborCentroid()));
108103
}

framework/src/linearfvkernels/LinearFVFluxKernel.C

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -193,6 +193,16 @@ LinearFVFluxKernel::singleSidedFaceArg(const FaceInfo * fi,
193193
return makeFace(*fi, limiter_type, true, correct_skewness);
194194
}
195195

196+
Real
197+
LinearFVFluxKernel::computeBoundaryFlux(const LinearFVBoundaryCondition & bc)
198+
{
199+
const auto elem_info = (_current_face_type == FaceInfo::VarFaceNeighbors::ELEM)
200+
? _current_face_info->elemInfo()
201+
: _current_face_info->neighborInfo();
202+
return computeBoundaryMatrixContribution(bc) * _var.getElemValue(*elem_info, determineState()) -
203+
computeBoundaryRHSContribution(bc);
204+
}
205+
196206
void
197207
LinearFVFluxKernel::setupFaceData(const FaceInfo * face_info)
198208
{

framework/src/systems/LinearSystem.C

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,9 @@
3535
#include "SolutionInvalidity.h"
3636
#include "MooseLinearVariableFV.h"
3737
#include "LinearFVTimeDerivative.h"
38+
#include "LinearFVFluxKernel.h"
39+
#include "LinearFVElementalKernel.h"
40+
#include "LinearFVBoundaryCondition.h"
3841

3942
// libMesh
4043
#include "libmesh/linear_solver.h"
@@ -134,6 +137,16 @@ LinearSystem::initialSetup()
134137

135138
for (auto * fv_kernel : fv_flux_kernels)
136139
fv_kernel->initialSetup();
140+
141+
std::vector<LinearFVBoundaryCondition *> fv_bcs;
142+
_fe_problem.theWarehouse()
143+
.query()
144+
.template condition<AttribSystem>("LinearFVBoundaryCondition")
145+
.template condition<AttribThread>(tid)
146+
.queryInto(fv_bcs);
147+
148+
for (auto * fv_bc : fv_bcs)
149+
fv_bc->initialSetup();
137150
}
138151
}
139152

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
# Conjugate Heat Transfer (CHT) Capability
2+
3+
This summarizes the design and details of the conjugate heat transfer capabilities
4+
with the linear finite volume system through the [SIMPLE.md] executioner.
5+
6+
This capability is activated by specifying a boundary on the [!param](/Executioner/SIMPLE/cht_interfaces)
7+
parameter. Other cht-related parameters can control the iteration between the solid and fluid
8+
energy equations. Once the capability is activated it will check if the
9+
used boundary conditions are compatible or not. In general, we introduced CHT versions of
10+
common boundary conditions such as [LinearFVRobinCHTBC.md] and [LinearFVDirichletCHTBC.md]
11+
that are dedicated for CHT applications.
12+
13+
For coupling purposes several new functors are created under the hood:
14+
15+
- +heat_flux_to_solid_*+ (where * is the interface boundary name),
16+
- +heat_flux_to_fluid_*+ (where * is the interface boundary name),
17+
- +interface_temperature_solid_*+ (where * is the interface boundary name),
18+
- +interface_temperature_fluid_*+ (where * is the interface boundary name),
19+
20+
where the first two describe the heat flux from one domain to the other, while the
21+
other express the interface temperatures from both sides.
22+
23+
## Energy Conservation Equations
24+
25+
The energy conservation equations for fluid and solid domains are:
26+
27+
\begin{equation}
28+
\frac{\partial \rho h_f}{\partial t} + \nabla \cdot \left(\rho \mathbf{u} h_f \right) = \nabla \cdot \left(k_f \nabla T_f\right) + Q_f\,,
29+
\end{equation}
30+
\begin{equation}
31+
\frac{\partial \rho h_s}{\partial t} = \nabla \cdot \left(k_s \nabla T_s\right) + Q_s\,,
32+
\end{equation}
33+
34+
Where $h_f = f(T_f)$ and $h_s = f(T_s)$ are the fluid and solid specific enthalpies, $k_f$ and $k_s$ are the thermal conductivities, and $Q_f$ and $Q_s$ are the external heat sources.
35+
36+
## Boundary Conditions
37+
38+
The coupling of the solid and fluid domains is done through boundary conditions that ensure:
39+
40+
1. **Continuity of Interface Temperature**
41+
\begin{equation}
42+
T_\mathrm{f,wall} = T_\mathrm{s,wall}
43+
\end{equation}
44+
45+
2. **Continuity of Conductive Flux at the Interface**
46+
\begin{equation}
47+
q_\mathrm{f,wall} = -q_\mathrm{s,wall}
48+
\end{equation}
49+
50+
## Coupling Methods
51+
52+
The methods currently recommended for CHT utilize [LinearFVDirichletCHTBC.md] and
53+
[LinearFVRobinCHTBC.md] in the two different ways listed below. The Robin BC can also
54+
emulate a Neumann BC by setting the [!param](/LinearFVBCs/LinearFVRobinCHTBC/h) parameter to 0.
55+
56+
- +Neumann-Dirichlet Coupling+
57+
58+
!algorithm
59+
[!function!begin name=NeumannDirichletCoupling]
60+
[!state text=Initialize $T_\mathrm{fluid,wall}^0$, $q_\mathrm{solid,wall}^0$]
61+
[!while!begin condition=Convergence criteria not met]
62+
[!state text=1. Solve fluid equation]
63+
[!state text=2. Update heat flux from fluid to solid $q_\mathrm{s,wall}^n$]
64+
[!state text=3. Solve solid equation]
65+
[!state text=4. Update boundary temperature $T_\mathrm{f,wall}^n$]
66+
[!while!end]
67+
[!function!end]
68+
69+
- +Robin-Robin Coupling+
70+
71+
!algorithm
72+
[!function!begin name=RobinRobinCoupling]
73+
[!state text=Initialize $T_\mathrm{fluid,wall}^0$, $q_\mathrm{s\rightarrow f}^0 = 0$]
74+
[!while!begin condition=Convergence criteria not met]
75+
[!state text=1. Solve fluid equation with Robin boundary condition using $T_\mathrm{s,wall}^{n-1}$ and $q_\mathrm{s\rightarrow f}^{n-1}$]
76+
[!state text=2. Update wall temperature $T_\mathrm{f,wall}^n$]
77+
[!state text=3. Update heat flux $q_\mathrm{f\rightarrow s}^n$]
78+
[!state text=4. Solve solid equation with Robin boundary condition using $T_\mathrm{f,wall}^{n}$ and $q_\mathrm{f\rightarrow s}^{n}$]
79+
[!state text=5. Update wall temperature $T_\mathrm{s,wall}^n$]
80+
[!state text=6. Update heat flux $q_\mathrm{s\rightarrow f}^n$]
81+
[!while!end]
82+
[!function!end]
83+
84+
85+
The Robin-Robin method introduces virtual heat transfer coefficients $h_f$ and $h_s$ to enhance stability and convergence.

modules/navier_stokes/doc/content/source/executioners/SIMPLE.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -153,6 +153,10 @@ Advected passive scalars do not affect the flow distribution, and therefore can
153153
pressure fields have been computed using the `SIMPLE` algorithm.
154154
Several systems may be used, for each passive scalar.
155155

156+
## Conjugate heat transfer
157+
158+
For the conjuagate heat transfer capabilities visit the [corresponding design page](linear_fv_cht.md)
159+
156160
!syntax parameters /Executioner/SIMPLE
157161

158162
!syntax inputs /Executioner/SIMPLE

modules/navier_stokes/doc/content/source/linearfvbcs/LinearFVConvectiveHeatTransferBC.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ object's and acts accordingly. To account for the heat flux on both sides of the
1717
the boundary condition should be used by both variables as
1818
shown in:
1919

20-
!listing modules/navier_stokes/test/tests/finite_volume/ins/cht/flow-around-square-linear.i block=LinearFVBCs
20+
!listing modules/navier_stokes/test/tests/finite_volume/ins/cht/bulk_heat_transfer/flow-around-square-linear.i block=LinearFVBCs
2121

2222
!syntax parameters /LinearFVBCs/LinearFVConvectiveHeatTransferBC
2323

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
# LinearFVDirichletCHTBC
2+
3+
## Description
4+
5+
This object is a boundary condition used in the Navier-Stokes module that can be used for conjugate heat transfer (CHT) problems.
6+
Its role is to enforce a fixed Dirichlet value at an interface where heat is exchanged between solid and fluid regions.
7+
In practice, it is a wrapper around [LinearFVAdvectionDiffusionFunctorDirichletBC.md] with additional content
8+
allowing error checking in CHT applications. For more information on the design of CHT, see [the CHT capability page](linear_fv_cht.md).
9+
10+
!listing modules/navier_stokes/test/tests/finite_volume/ins/cht/conjugate_heat_transfer/cht_neu-dir.i block=fluid_solid solid_fluid
11+
12+
!syntax parameters /LinearFVBCs/LinearFVDirichletCHTBC
13+
14+
!syntax inputs /LinearFVBCs/LinearFVDirichletCHTBC
15+
16+
!syntax children /LinearFVBCs/LinearFVDirichletCHTBC
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
# LinearFVRobinCHTBC
2+
3+
## Description
4+
5+
This object is a boundary condition used in the Navier-Stokes module that can be used for conjugate heat transfer (CHT) problems.
6+
Its role is to enforce a Robin-type boundary condition at an interface where heat is exchanged between solid and fluid regions.
7+
It is similar in behavior to [LinearFVAdvectionDiffusionFunctorRobinBC.md] with the
8+
coefficients in the expression aligned with the thermal-hydraulics fields.
9+
For more information on the design of CHT, see [the CHT capability page](linear_fv_cht.md).
10+
11+
This boundary condition needs an incoming flux which is typically provided by the
12+
SIMPLE-type executioner when conjugate heat transfer is enabled. The
13+
automatically created functors within [SIMPLE.md] are:
14+
15+
- heat_flux_to_solid_* (where * is the interface boundary name)
16+
- heat_flux_to_fluid_* (where * is the interface boundary name)
17+
18+
When this boundary condition is action on the fluid side the user is
19+
recommended to set [!param](/LinearFVBCs/LinearFVRobinCHTBC/incoming_flux) parameter to
20+
the `heat_flux_to_fluid` functor. The same logic applies to the solid side.
21+
Furthermore, this boundary condition also requires a surface temperature which
22+
is typically the surface temperature on the other side of the interface.
23+
The interface temperatures are also tracked in fuctors and are created within the
24+
[SIMPLE.md] executioner. The following surface termperatures are created automatically:
25+
26+
- interface_temperature_solid_* (where * is the interface boundary name)
27+
- interface_temperature_fluid_* (where * is the interface boundary name)
28+
29+
!listing modules/navier_stokes/test/tests/finite_volume/ins/cht/conjugate_heat_transfer/cht_rob-rob.i block=fluid_solid solid_fluid
30+
31+
!syntax parameters /LinearFVBCs/LinearFVRobinCHTBC
32+
33+
!syntax inputs /LinearFVBCs/LinearFVRobinCHTBC
34+
35+
!syntax children /LinearFVBCs/LinearFVRobinCHTBC

0 commit comments

Comments
 (0)