3535/* !
3636 * \brief Unlimited reconstruction.
3737 */
38- template <size_t nVar, size_t nDim, class Gradient_t >
38+ template <size_t nVarGrad_ = 0 , size_t nVar, size_t nDim, class Gradient_t >
3939FORCEINLINE void musclUnlimited (Int iPoint,
4040 const VectorDbl<nDim>& vector_ij,
4141 Double scale,
4242 const Gradient_t& gradient,
4343 VectorDbl<nVar>& vars) {
44- auto grad = gatherVariables<nVar,nDim>(iPoint, gradient);
45- for (size_t iVar = 0 ; iVar < nVar; ++iVar) {
44+ constexpr auto nVarGrad = nVarGrad_ > 0 ? nVarGrad_ : nVar;
45+ auto grad = gatherVariables<nVarGrad,nDim>(iPoint, gradient);
46+ for (size_t iVar = 0 ; iVar < nVarGrad; ++iVar) {
4647 vars (iVar) += scale * dot (grad[iVar], vector_ij);
4748 }
4849}
4950
5051/* !
5152 * \brief Limited reconstruction with point-based limiter.
5253 */
53- template <size_t nVar, size_t nDim, class Limiter_t , class Gradient_t >
54+ template <size_t nVarGrad_ = 0 , size_t nVar, size_t nDim, class Limiter_t , class Gradient_t >
5455FORCEINLINE void musclPointLimited (Int iPoint,
5556 const VectorDbl<nDim>& vector_ij,
5657 Double scale,
5758 const Limiter_t& limiter,
5859 const Gradient_t& gradient,
5960 VectorDbl<nVar>& vars) {
60- auto lim = gatherVariables<nVar>(iPoint, limiter);
61- auto grad = gatherVariables<nVar,nDim>(iPoint, gradient);
62- for (size_t iVar = 0 ; iVar < nVar; ++iVar) {
61+ constexpr auto nVarGrad = nVarGrad_ > 0 ? nVarGrad_ : nVar;
62+ auto lim = gatherVariables<nVarGrad>(iPoint, limiter);
63+ auto grad = gatherVariables<nVarGrad,nDim>(iPoint, gradient);
64+ for (size_t iVar = 0 ; iVar < nVarGrad; ++iVar) {
6365 vars (iVar) += lim (iVar) * scale * dot (grad[iVar], vector_ij);
6466 }
6567}
6668
6769/* !
6870 * \brief Limited reconstruction with edge-based limiter.
6971 */
70- template <size_t nDim, class VarType , class Gradient_t >
72+ template <size_t nVarGrad_ = 0 , size_t nDim, class VarType , class Gradient_t >
7173FORCEINLINE void musclEdgeLimited (Int iPoint,
7274 Int jPoint,
7375 const VectorDbl<nDim>& vector_ij,
7476 const Gradient_t& gradient,
7577 CPair<VarType>& V) {
76- constexpr size_t nVar = VarType::nVar;
78+ constexpr auto nVarGrad = nVarGrad_ > 0 ? nVarGrad_ : VarType::nVar;
7779
78- auto grad_i = gatherVariables<nVar ,nDim>(iPoint, gradient);
79- auto grad_j = gatherVariables<nVar ,nDim>(jPoint, gradient);
80+ auto grad_i = gatherVariables<nVarGrad ,nDim>(iPoint, gradient);
81+ auto grad_j = gatherVariables<nVarGrad ,nDim>(jPoint, gradient);
8082
81- for (size_t iVar = 0 ; iVar < nVar ; ++iVar) {
83+ for (size_t iVar = 0 ; iVar < nVarGrad ; ++iVar) {
8284 const Double proj_i = dot (grad_i[iVar], vector_ij);
8385 const Double proj_j = dot (grad_j[iVar], vector_ij);
8486 const Double delta_ij = V.j .all (iVar) - V.i .all (iVar);
@@ -93,15 +95,21 @@ FORCEINLINE void musclEdgeLimited(Int iPoint,
9395
9496/* !
9597 * \brief Retrieve primitive variables for points i/j, reconstructing them if needed.
98+ * \note Density and enthalpy are recomputed from ideal gas EOS.
9699 * \param[in] iEdge, iPoint, jPoint - Edge and its nodes.
100+ * \param[in] gamma - Heat capacity ratio.
101+ * \param[in] gasConst - Specific gas constant.
97102 * \param[in] muscl - If true, reconstruct, else simply fetch.
103+ * \param[in] limiterType - Type of flux limiter.
98104 * \param[in] V1st - Pair of compressible flow primitives for nodes i,j.
99105 * \param[in] vector_ij - Distance vector from i to j.
100106 * \param[in] solution - Entire solution container (a derived CVariable).
101107 * \return Pair of primitive variables.
102108 */
103109template <class ReconVarType , class PrimVarType , size_t nDim, class VariableType >
104110FORCEINLINE CPair<ReconVarType> reconstructPrimitives (Int iEdge, Int iPoint, Int jPoint,
111+ const su2double& gamma,
112+ const su2double& gasConst,
105113 bool muscl, LIMITER limiterType,
106114 const CPair<PrimVarType>& V1st,
107115 const VectorDbl<nDim>& vector_ij,
@@ -119,19 +127,29 @@ FORCEINLINE CPair<ReconVarType> reconstructPrimitives(Int iEdge, Int iPoint, Int
119127 }
120128
121129 if (muscl) {
130+ /* --- Recompute density and enthalpy instead of reconstructing. ---*/
131+ constexpr auto nVarGrad = ReconVarType::nVar - 2 ;
132+
122133 switch (limiterType) {
123134 case LIMITER::NONE:
124- musclUnlimited (iPoint, vector_ij, 0.5 , gradients, V.i .all );
125- musclUnlimited (jPoint, vector_ij,-0.5 , gradients, V.j .all );
135+ musclUnlimited<nVarGrad> (iPoint, vector_ij, 0.5 , gradients, V.i .all );
136+ musclUnlimited<nVarGrad> (jPoint, vector_ij,-0.5 , gradients, V.j .all );
126137 break ;
127138 case LIMITER::VAN_ALBADA_EDGE:
128- musclEdgeLimited (iPoint, jPoint, vector_ij, gradients, V);
139+ musclEdgeLimited<nVarGrad> (iPoint, jPoint, vector_ij, gradients, V);
129140 break ;
130141 default :
131- musclPointLimited (iPoint, vector_ij, 0.5 , limiters, gradients, V.i .all );
132- musclPointLimited (jPoint, vector_ij,-0.5 , limiters, gradients, V.j .all );
142+ musclPointLimited<nVarGrad> (iPoint, vector_ij, 0.5 , limiters, gradients, V.i .all );
143+ musclPointLimited<nVarGrad> (jPoint, vector_ij,-0.5 , limiters, gradients, V.j .all );
133144 break ;
134145 }
146+ V.i .density () = V.i .pressure () / (gasConst * V.i .temperature ());
147+ V.j .density () = V.j .pressure () / (gasConst * V.j .temperature ());
148+
149+ const su2double cp = gasConst * gamma / (gamma - 1 );
150+ V.i .enthalpy () = cp * V.i .temperature () + 0.5 * squaredNorm<nDim>(V.i .velocity ());
151+ V.j .enthalpy () = cp * V.j .temperature () + 0.5 * squaredNorm<nDim>(V.j .velocity ());
152+
135153 /* --- Detect a non-physical reconstruction based on negative pressure or density. ---*/
136154 const Double neg_p_or_rho = fmax (fmin (V.i .pressure (), V.j .pressure ()) < 0.0 ,
137155 fmin (V.i .density (), V.j .density ()) < 0.0 );
0 commit comments