#if defined(NAVIERSTOKES) MODULE WallFunctionBC USE SMConstants USE PhysicsStorage IMPLICIT NONE ! ! ***************************** ! Default everything to private ! ***************************** ! PRIVATE ! ! **************** ! Public variables ! **************** ! ! ! ****************** ! Public definitions ! ****************** ! PUBLIC WallViscousFlux, wall_shear, u_tau_f, u_tau_f_ABL, y_plus_f, u_plus_f ! CONTAINS ! !------------------------------------------------------------------------------------------------------------------------ ! ! Wall shear stress is computed here using the Reichardt model ! following Frere et al 2017. ! Wall shear stress (tau_w) is then used to compute the viscous flux. ! The viscous flux is set in the same direction as the parallel velocity. ! If the reference velocity parallel to the wall is less than a ! minimum value, flux is set to zero to avoid numerical issues. SUBROUTINE WallViscousFlux (U_inst, dWall, nHat, rho, mu, U_avg, visc_flux, u_tau) use WallFunctionDefinitions, only: useAverageV IMPLICIT NONE REAL(kind=RP) , INTENT(IN) :: U_inst(NDIM) ! Instantaneous velocity from LES solver REAL(kind=RP) , INTENT(IN) :: dWall ! Normal wall distance REAL(kind=RP), INTENT(IN) :: nHat(NDIM) ! Unitary vector normal to wall REAL(kind=RP) , INTENT(IN) :: rho ! Density REAL(kind=RP) , INTENT(IN) :: mu ! Dynamic viscosity REAL(kind=RP) , INTENT(IN) :: U_avg(NDIM) ! Mean (in time) velocity from LES solver REAL(kind=RP) , INTENT(INOUT) :: visc_flux(NCONS) ! Viscous Flux REAL(kind=RP) , INTENT(INOUT) :: u_tau ! friction velocity !local variables REAL(kind=RP), DIMENSION(NDIM) :: x_II ! Unitary vector parallel to wall REAL(kind=RP), DIMENSION(NDIM) :: U_ref ! Reference Velocity REAL(kind=RP), DIMENSION(NDIM) :: u_parallel ! Velocity parallel to wall REAL(kind=RP), DIMENSION(NDIM) :: u_parallel_aux ! Velocity parallel to wall auxiliary, is the instantaneous when the average is used REAL(kind=RP) :: u_II ! Velocity magnitude parallel to wall, used in Wall Function REAL(kind=RP) :: tau_w ! Wall shear stress REAL(kind=RP) :: beta ! damping factor from Thomas et. al if (useAverageV) then U_ref = U_avg else U_ref = U_inst end if u_parallel = U_ref - (dot_product(U_ref, nHat) * nHat) x_II = u_parallel / norm2(u_parallel) u_II = dot_product(U_ref, x_II) ! Wall model only modifies momentum viscous fluxes. call wall_shear(u_II, dWall, rho, mu, tau_w, u_tau) ! visc_flux(IRHOU:IRHOW) = - tau_w_f (u_II,dWall,rho,mu) * x_II if (useAverageV) then u_parallel_aux = U_inst - (dot_product(U_inst, nHat) * nHat) x_II = u_parallel_aux / u_II !schuman, the direction scales with the instantaneous values ! beta = 0.3_RP ! thomas arbitrary value. If set to 0.0_RP, the schuman eq is recovered ! x_II = (beta * u_parallel_aux + (1-beta) * u_parallel) / u_II ! thomas, the direction scales with both the instantaneous and the mean end if visc_flux(IRHOU:IRHOW) = - tau_w * x_II ! print *, "visc_flux: ", visc_flux END SUBROUTINE ! !------------------------------------------------------------------------------------------------------------------------ ! ! FUNCTION tau_w_f (u_II, y, rho, mu) SUBROUTINE wall_shear(u_II, y, rho, mu, tau_w, u_tau) USE WallFunctionDefinitions, ONLY: wallFuncIndex, STD_WALL, ABL_WALL IMPLICIT NONE REAL(kind=RP), INTENT(IN) :: u_II ! Mean streamwise velocity parallel to the wall REAL(kind=RP), INTENT(IN) :: y ! Normal wall distance REAL(kind=RP), INTENT(IN) :: rho ! Density REAL(kind=RP), INTENT(IN) :: mu ! Dynamic viscosity REAL(kind=RP), INTENT(OUT) :: tau_w ! (OUT) Wall shear stress REAL(kind=RP), INTENT(INOUT) :: u_tau ! Friction velocity ! REAL(kind=RP) :: tau_w_f ! (OUT) Wall shear stress ! REAL(kind=RP) :: u_tau ! Friction velocity REAL(kind=RP) :: nu ! Kinematic viscosity nu = mu / rho select case (wallFuncIndex) case (STD_WALL) ! u_tau is computed by solving Eq. (3) in Frere et al 2017 ! along with the definitions of u+ and y+. ! use previous solution as the new starting point u_tau = u_tau_f( u_II, y, nu, u_tau ) case (ABL_WALL) ! print *, "u_II: ", u_II, " z: ", y u_tau = u_tau_f_ABL( u_II, y, nu ) ! print *, "u_tau: ", u_tau end select ! then the definition of the wall shear stress is used tau_w = rho * u_tau * u_tau END SUBROUTINE ! END FUNCTION ! !------------------------------------------------------------------------------------------------------------------------ ! FUNCTION u_tau_f (u_II,y,nu, u_tau0) USE WallFunctionDefinitions, ONLY: newtonTol, newtonAlpha, newtonMaxIter ! USE WallFunctionDefinitions, ONLY: newtonTol, newtonAlpha, newtonMaxIter, u_tau0 IMPLICIT NONE REAL(kind=RP), INTENT(IN) :: u_II ! Mean streamwise velocity parallel to the wall REAL(kind=RP), INTENT(IN) :: y ! Normal wall distance REAL(kind=RP), INTENT(IN) :: nu ! Kinematic viscosity REAL(kind=RP), INTENT(IN) :: u_tau0 ! REAL(kind=RP) :: u_tau_f ! Friction velocity REAL(kind=RP) :: u_tau ! Previous value for Newton method REAL(kind=RP) :: u_tau_next ! Next value for Newton method INTEGER :: i ! Counter REAL(kind=RP) :: Aux_x0 ! Objective function evaluated at x0 REAL(kind=RP) :: JAC ! Derivate of objective function evaluated at x0 REAL(kind=RP) :: eps ! Size of the perturbation to compute numerical der. REAL(kind=RP) :: alpha ! Parameter for the damped Newton method ! The value of u_tau is found by solving a non linear equation. ! The damped Newton method is used. ! Initial seed for Newton method u_tau = u_tau0 ! Iterate in Newton's method until convergence criteria is met DO i = 1, newtonMaxIter ! Evaluate auxiliary function at u_tau Aux_x0 = Aux_f ( u_tau , u_II, y, nu ) ! Compute numerical derivative of auxiliary function at u_tau eps = ABS(u_tau) * 1.0E-8_RP JAC = ( Aux_f ( u_tau + eps, u_II, y, nu ) - Aux_x0 ) / eps ! Default value for alpha (Newton method) alpha = newtonAlpha ! Damped alpha parameter for the Damped Newton method DO WHILE ( ABS( Aux_x0 ) < ABS( Aux_f(u_tau - Aux_x0 / JAC * alpha, u_II, y, nu ) ) ) alpha = alpha / 2 END DO ! Damped Newton step u_tau_next = u_tau - Aux_x0 / JAC * alpha ! Convergence criteria for Newton's method IF ( ( ABS ( ( u_tau_next - u_tau ) / u_tau ) < newtonTol ) & .AND. & ( ABS ( Aux_x0 ) < newtonTol ) ) THEN ! Assign output value to u_tau u_tau_f = u_tau_next RETURN END IF ! Set value for u_tau for next iteration u_tau = u_tau_next END DO error stop "DAMPED NEWTON METHOD IN WALL FUNCTION DOES NOT CONVERGE." END FUNCTION ! !------------------------------------------------------------------------------------------------------------------------ ! FUNCTION Aux_f (u_tau, u_II, y, nu) IMPLICIT NONE REAL(kind=RP), INTENT(IN) :: u_tau REAL(kind=RP), INTENT(IN) :: u_II REAL(kind=RP), INTENT(IN) :: y REAL(kind=RP), INTENT(IN) :: nu REAL(kind=RP) :: Aux_f ! (OUT) ! Auxiliary function is evaluated at x0 ! When Aux_f = 0 The definition of the ! dimensionless mean streamwise velocity ! parallel to the wall is recovered and ! a valid value for u_tau is found. ! Aux_f = 0 -> u_II / u_tau = u_plus Aux_f = u_II - u_plus_f ( y_plus_f ( y, u_tau, nu ) ) * u_tau END FUNCTION ! !------------------------------------------------------------------------------------------------------------------------ ! PURE FUNCTION u_plus_f (y_plus) USE WallFunctionDefinitions, ONLY: kappa, WallC IMPLICIT NONE ! Definition of u_plus ! Reichardt law-of-the-wall (taken from Frere et al 2017 Eq. (3)) REAL(kind=RP), INTENT(IN) :: y_plus REAL(kind=RP) :: u_plus_f ! (OUT) u_plus_f = 1.0_RP / kappa * log( 1.0_RP + kappa * y_plus ) & + ( WallC - 1.0_RP / kappa * log(kappa) ) * & ( 1.0_RP - exp( -y_plus / 11.0_RP )-( y_plus / 11.0_RP ) * exp( -y_plus / 3.0_RP ) ) END FUNCTION ! !------------------------------------------------------------------------------------------------------------------------ ! PURE FUNCTION y_plus_f (y, u_tau, nu) ! Definition of y_plus (taken from Frere et al 2017) REAL(kind=RP), INTENT(IN) :: y REAL(kind=RP), INTENT(IN) :: u_tau REAL(kind=RP), INTENT(IN) :: nu REAL(kind=RP) :: y_plus_f ! (OUT) y_plus_f = y * u_tau / nu END FUNCTION ! !------------------------------------------------------------------------------------------------------------------------ ! FUNCTION u_tau_f_ABL (u_II,y,nu) USE WallFunctionDefinitions, ONLY: y0, d, kappa IMPLICIT NONE REAL(kind=RP), INTENT(IN) :: u_II ! Mean streamwise velocity parallel to the wall REAL(kind=RP), INTENT(IN) :: y ! Normal wall distance REAL(kind=RP), INTENT(IN) :: nu ! Kinematic viscosity REAL(kind=RP) :: u_tau_f_ABL ! (OUT) Friction velocity u_tau_f_ABL = kappa * u_II / log( (y-d) / y0 ) END FUNCTION u_tau_f_ABL ! !------------------------------------------------------------------------------------------------------------------------ ! END MODULE #endif