LCOV - code coverage report
Current view: top level - src/fvbcs - INSFVTurbulentViscosityWallFunction.C (source / functions) Hit Total Coverage
Test: idaholab/moose navier_stokes: 9fc4b0 Lines: 73 76 96.1 %
Date: 2025-08-14 10:14:56 Functions: 3 3 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : //* This file is part of the MOOSE framework
       2             : //* https://mooseframework.inl.gov
       3             : //*
       4             : //* All rights reserved, see COPYRIGHT for full restrictions
       5             : //* https://github.com/idaholab/moose/blob/master/COPYRIGHT
       6             : //*
       7             : //* Licensed under LGPL 2.1, please see LICENSE for details
       8             : //* https://www.gnu.org/licenses/lgpl-2.1.html
       9             : 
      10             : #include "INSFVTurbulentViscosityWallFunction.h"
      11             : #include "Function.h"
      12             : #include "NavierStokesMethods.h"
      13             : 
      14             : registerMooseObject("NavierStokesApp", INSFVTurbulentViscosityWallFunction);
      15             : 
      16             : InputParameters
      17        1916 : INSFVTurbulentViscosityWallFunction::validParams()
      18             : {
      19        1916 :   InputParameters params = FVDirichletBCBase::validParams();
      20        1916 :   params.addClassDescription("Adds Dirichlet BC for wall values of the turbulent viscosity.");
      21        3832 :   params.addRequiredParam<MooseFunctorName>("u", "The velocity in the x direction.");
      22        3832 :   params.addParam<MooseFunctorName>("v", "The velocity in the y direction.");
      23        3832 :   params.addParam<MooseFunctorName>("w", "The velocity in the z direction.");
      24        1916 :   params.addRequiredParam<MooseFunctorName>(NS::density, "Density");
      25        1916 :   params.addRequiredParam<MooseFunctorName>(NS::mu, "Dynamic viscosity.");
      26        1916 :   params.addRequiredParam<MooseFunctorName>(NS::mu_t, "The turbulent viscosity.");
      27        3832 :   params.addParam<MooseFunctorName>("k", "The turbulent kinetic energy.");
      28        3832 :   params.deprecateParam("k", NS::TKE, "01/01/2025");
      29        3832 :   params.addParam<Real>("C_mu", 0.09, "Coupled turbulent kinetic energy closure.");
      30             : 
      31        3832 :   MooseEnum wall_treatment("eq_newton eq_incremental eq_linearized neq", "neq");
      32        3832 :   params.addParam<MooseEnum>(
      33             :       "wall_treatment", wall_treatment, "The method used for computing the wall functions");
      34        1916 :   return params;
      35        1916 : }
      36             : 
      37         441 : INSFVTurbulentViscosityWallFunction::INSFVTurbulentViscosityWallFunction(
      38         441 :     const InputParameters & params)
      39             :   : FVDirichletBCBase(params),
      40         441 :     _dim(_subproblem.mesh().dimension()),
      41         882 :     _u_var(getFunctor<ADReal>("u")),
      42        1323 :     _v_var(params.isParamValid("v") ? &(getFunctor<ADReal>("v")) : nullptr),
      43         441 :     _w_var(params.isParamValid("w") ? &(getFunctor<ADReal>("w")) : nullptr),
      44         441 :     _rho(getFunctor<ADReal>(NS::density)),
      45         441 :     _mu(getFunctor<ADReal>(NS::mu)),
      46         441 :     _mu_t(getFunctor<ADReal>(NS::mu_t)),
      47         441 :     _k(getFunctor<ADReal>(NS::TKE)),
      48         882 :     _C_mu(getParam<Real>("C_mu")),
      49         882 :     _wall_treatment(getParam<MooseEnum>("wall_treatment").getEnum<NS::WallTreatmentEnum>()),
      50         882 :     _preserve_sparsity_pattern(_fv_problem.preserveMatrixSparsityPattern())
      51             : {
      52         441 : }
      53             : 
      54             : ADReal
      55      389040 : INSFVTurbulentViscosityWallFunction::boundaryValue(const FaceInfo & fi,
      56             :                                                    const Moose::StateArg & /* state */) const
      57             : {
      58             :   // if on an internal face (internal to the mesh, but an external boundary of the flow area),
      59             :   // we have to select the element on which the flow variables / viscosity is defined
      60             :   const bool use_elem = (fi.faceType(_var_sys_numbers_pair) == FaceInfo::VarFaceNeighbors::ELEM);
      61             :   const Real wall_dist = std::abs(
      62      389040 :       ((use_elem ? fi.elemCentroid() : fi.neighborCentroid()) - fi.faceCentroid()) * fi.normal());
      63      389040 :   const Elem * const elem_ptr = use_elem ? fi.elemPtr() : fi.neighborPtr();
      64      389040 :   const auto elem_arg = makeElemArg(elem_ptr);
      65             : 
      66             :   // Get the previous non linear iteration values
      67             :   const auto old_state = Moose::StateArg(1, Moose::SolutionIterationType::Nonlinear);
      68      389040 :   const auto mu = _mu(elem_arg, old_state);
      69      389040 :   const auto rho = _rho(elem_arg, old_state);
      70             : 
      71             :   // Get the velocity vector
      72      778080 :   ADRealVectorValue velocity(_u_var(elem_arg, old_state));
      73      389040 :   if (_v_var)
      74      389040 :     velocity(1) = (*_v_var)(elem_arg, old_state);
      75      389040 :   if (_w_var)
      76           0 :     velocity(2) = (*_w_var)(elem_arg, old_state);
      77             : 
      78             :   // Compute the velocity and direction of the velocity component that is parallel to the wall
      79             :   const auto parallel_speed =
      80     1167120 :       NS::computeSpeed<ADReal>(velocity - velocity * (fi.normal()) * (fi.normal()));
      81             : 
      82             :   // Switch for determining the near wall quantities
      83             :   // wall_treatment can be: "eq_newton eq_incremental eq_linearized neq"
      84             :   ADReal y_plus;
      85             :   ADReal mut_log; // turbulent log-layer viscosity
      86             :   ADReal mu_wall; // total wall viscosity to obtain the shear stress at the wall
      87             : 
      88      389040 :   if (_wall_treatment == NS::WallTreatmentEnum::EQ_NEWTON)
      89             :   {
      90             :     // Full Newton-Raphson solve to find the wall quantities from the law of the wall
      91      341160 :     const auto u_tau = NS::findUStar<ADReal>(mu, rho, parallel_speed, wall_dist);
      92      341160 :     y_plus = wall_dist * u_tau * rho / mu;
      93      341160 :     mu_wall = rho * Utility::pow<2>(u_tau) * wall_dist / parallel_speed;
      94      341160 :     mut_log = mu_wall - mu;
      95             :   }
      96       47880 :   else if (_wall_treatment == NS::WallTreatmentEnum::EQ_INCREMENTAL)
      97             :   {
      98             :     // Incremental solve on y_plus to get the near-wall quantities
      99       21960 :     y_plus = NS::findyPlus<ADReal>(mu, rho, std::max(parallel_speed, 1e-10), wall_dist);
     100           0 :     mu_wall = mu * (NS::von_karman_constant * y_plus /
     101       65880 :                     std::log(std::max(NS::E_turb_constant * y_plus, 1 + 1e-4)));
     102       21960 :     mut_log = mu_wall - mu;
     103             :   }
     104       25920 :   else if (_wall_treatment == NS::WallTreatmentEnum::EQ_LINEARIZED)
     105             :   {
     106             :     // Linearized approximation to the wall function to find the near-wall quantities faster
     107       12960 :     const ADReal a_c = 1 / NS::von_karman_constant;
     108       25920 :     const ADReal b_c = 1 / NS::von_karman_constant *
     109       38880 :                        (std::log(NS::E_turb_constant * std::max(wall_dist, 1.0) / mu) + 1.0);
     110       12960 :     const ADReal c_c = parallel_speed;
     111             : 
     112       64800 :     const auto u_tau = (-b_c + std::sqrt(std::pow(b_c, 2) + 4.0 * a_c * c_c)) / (2.0 * a_c);
     113       12960 :     y_plus = wall_dist * u_tau * rho / mu;
     114       12960 :     mu_wall = rho * Utility::pow<2>(u_tau) * wall_dist / parallel_speed;
     115       12960 :     mut_log = mu_wall - mu;
     116             :   }
     117       12960 :   else if (_wall_treatment == NS::WallTreatmentEnum::NEQ)
     118             :   {
     119             :     // Assign non-equilibrium wall function value
     120       25920 :     y_plus = std::pow(_C_mu, 0.25) * wall_dist * std::sqrt(_k(elem_arg, old_state)) * rho / mu;
     121           0 :     mu_wall = mu * (NS::von_karman_constant * y_plus /
     122       38880 :                     std::log(std::max(NS::E_turb_constant * y_plus, 1.0 + 1e-4)));
     123       12960 :     mut_log = mu_wall - mu;
     124             :   }
     125             :   else
     126             :     mooseAssert(false,
     127             :                 "For `INSFVTurbulentViscosityWallFunction` , wall treatment should not reach here");
     128             : 
     129      389040 :   ADReal residual = 0;
     130             :   // To keep the same sparsity pattern for all y_plus
     131      389040 :   if (_preserve_sparsity_pattern)
     132      778080 :     residual = 0 * mut_log * y_plus;
     133             : 
     134      389040 :   if (y_plus <= 5.0)
     135             :     // sub-laminar layer
     136             :     residual += 0.0;
     137      135408 :   else if (y_plus >= 30.0)
     138             :     // log-layer
     139      119466 :     residual += std::max(mut_log, NS::mu_t_low_limit);
     140             :   else
     141             :   {
     142             :     // buffer layer
     143       15942 :     const auto blending_function = (y_plus - 5.0) / 25.0;
     144             :     // the blending depends on the mut_log at y+=30
     145       15942 :     const auto mut_log = mu * _mut_30;
     146       15942 :     residual += std::max(blending_function * mut_log, NS::mu_t_low_limit);
     147             :   }
     148      389040 :   return residual;
     149             : }

Generated by: LCOV version 1.14