LCOV - code coverage report
Current view: top level - star/private - hydro_rsp2.f90 (source / functions) Coverage Total Hit
Test: coverage.info Lines: 0.0 % 579 0
Test Date: 2025-12-14 16:52:03 Functions: 0.0 % 34 0

            Line data    Source code
       1              : ! ***********************************************************************
       2              : !
       3              : !   Copyright (C) 2010-2020  The MESA Team
       4              : !
       5              : !   This program is free software: you can redistribute it and/or modify
       6              : !   it under the terms of the GNU Lesser General Public License
       7              : !   as published by the Free Software Foundation,
       8              : !   either version 3 of the License, or (at your option) any later version.
       9              : !
      10              : !   This program is distributed in the hope that it will be useful,
      11              : !   but WITHOUT ANY WARRANTY; without even the implied warranty of
      12              : !   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
      13              : !   See the GNU Lesser General Public License for more details.
      14              : !
      15              : !   You should have received a copy of the GNU Lesser General Public License
      16              : !   along with this program. If not, see <https://www.gnu.org/licenses/>.
      17              : !
      18              : ! ***********************************************************************
      19              : 
      20              :       module hydro_rsp2
      21              : 
      22              :       use star_private_def
      23              :       use const_def, only: dp, boltz_sigma, pi, clight, crad, ln10
      24              :       use utils_lib, only: is_bad
      25              :       use auto_diff
      26              :       use auto_diff_support
      27              :       use accurate_sum_auto_diff_star_order1
      28              :       use star_utils
      29              : 
      30              :       implicit none
      31              : 
      32              :       private
      33              :       public :: do1_rsp2_L_eqn
      34              :       public :: do1_turbulent_energy_eqn
      35              :       public :: do1_rsp2_Hp_eqn
      36              :       public :: compute_Eq_cell
      37              :       public :: compute_Uq_face
      38              :       public :: set_RSP2_vars
      39              :       public :: Hp_face_for_rsp2_val
      40              :       public :: Hp_face_for_rsp2_eqn, set_etrb_start_vars
      41              :       public :: RSP2_adjust_vars_before_call_solver
      42              :       public :: get_RSP2_alfa_beta_face_weights
      43              : 
      44              :       real(dp), parameter :: &
      45              :          x_ALFAP = 2.d0/3.d0, &  ! Ptrb
      46              :          x_ALFAS = (1.d0/2.d0)*sqrt_2_div_3, &  ! PII_face and Lc
      47              :          x_ALFAC = (1.d0/2.d0)*sqrt_2_div_3, &  ! Lc
      48              :          x_CEDE  = (8.d0/3.d0)*sqrt_2_div_3, &  ! DAMP
      49              :          x_GAMMAR = 2.d0*sqrt(3.d0)  ! DAMPR
      50              : 
      51              :       contains
      52              : 
      53            0 :       subroutine set_RSP2_vars(s,ierr)
      54              :          type (star_info), pointer :: s
      55              :          integer, intent(out) :: ierr
      56              :          type(auto_diff_real_star_order1) :: x
      57              :          integer :: k, op_err
      58              :          include 'formats'
      59            0 :          ierr = 0
      60            0 :          op_err = 0
      61            0 :          !$OMP PARALLEL DO PRIVATE(k,op_err) SCHEDULE(dynamic,2)
      62              :          do k=1,s%nz
      63              :             ! Hp_face(k) <= 0 means it needs to be set.  e.g., after read file
      64              :             if (s% Hp_face(k) <= 0) then
      65              :                s% Hp_face(k) = get_scale_height_face_val(s,k)
      66              :                s% xh(s% i_Hp,k) = s% Hp_face(k)
      67              :             end if
      68              :             x = compute_Y_face(s, k, op_err)
      69              :             if (op_err /= 0) ierr = op_err
      70              :             x = compute_PII_face(s, k, op_err)
      71              :             if (op_err /= 0) ierr = op_err
      72              :             !Pvsc           skip?
      73              :          end do
      74              :          !$OMP END PARALLEL DO
      75            0 :          if (ierr /= 0) then
      76            0 :             if (s% report_ierr) write(*,2) 'failed in set_RSP2_vars loop 1', s% model_number
      77            0 :             return
      78              :          end if
      79            0 :          !$OMP PARALLEL DO PRIVATE(k,op_err) SCHEDULE(dynamic,2)
      80              :          do k=1,s% nz
      81              :             x = compute_Chi_cell(s, k, op_err)
      82              :             if (op_err /= 0) ierr = op_err
      83              :             x = compute_Eq_cell(s, k, op_err)
      84              :             if (op_err /= 0) ierr = op_err
      85              :             x = compute_C(s, k, op_err)  ! COUPL
      86              :             if (op_err /= 0) ierr = op_err
      87              :             x = compute_L_face(s, k, op_err)  ! Lr, Lt, Lc
      88              :             if (op_err /= 0) ierr = op_err
      89              :          end do
      90              :          !$OMP END PARALLEL DO
      91            0 :          if (ierr /= 0) then
      92            0 :             if (s% report_ierr) write(*,2) 'failed in set_RSP2_vars loop 2', s% model_number
      93            0 :             return
      94              :          end if
      95            0 :          do k = 1, s% RSP2_num_outermost_cells_forced_nonturbulent
      96            0 :             s% Eq(k) = 0d0; s% Eq_ad(k) = 0d0
      97            0 :             s% Chi(k) = 0d0; s% Chi_ad(k) = 0d0
      98            0 :             s% COUPL(k) = 0d0; s% COUPL_ad(k) = 0d0
      99              :             !s% Ptrb(k) = 0d0;
     100            0 :             s% Lc(k) = 0d0; s% Lc_ad(k) = 0d0
     101            0 :             s% Lt(k) = 0d0; s% Lt_ad(k) = 0d0
     102              :          end do
     103            0 :          do k = s% nz + 1 - int(s% nz/s% RSP2_nz_div_IBOTOM) , s% nz
     104            0 :             s% Eq(k) = 0d0; s% Eq_ad(k) = 0d0
     105            0 :             s% Chi(k) = 0d0; s% Chi_ad(k) = 0d0
     106            0 :             s% COUPL(k) = 0d0; s% COUPL_ad(k) = 0d0
     107              :             !s% Ptrb(k) = 0d0;
     108            0 :             s% Lc(k) = 0d0; s% Lc_ad(k) = 0d0
     109            0 :             s% Lt(k) = 0d0; s% Lt_ad(k) = 0d0
     110              :          end do
     111              :       end subroutine set_RSP2_vars
     112              : 
     113              : 
     114            0 :       subroutine do1_rsp2_L_eqn(s, k, nvar, ierr)
     115              :          use star_utils, only: save_eqn_residual_info
     116              :          type (star_info), pointer :: s
     117              :          integer, intent(in) :: k, nvar
     118              :          integer, intent(out) :: ierr
     119              :          type(auto_diff_real_star_order1) ::  &
     120              :             L_expected, L_actual,resid
     121            0 :          real(dp) :: scale, residual, L_start_max
     122              :          logical :: test_partials
     123              :          include 'formats'
     124              : 
     125              :          !test_partials = (k == s% solver_test_partials_k)
     126            0 :          test_partials = .false.
     127            0 :          if (.not. s% RSP2_flag) then
     128            0 :             ierr = -1
     129            0 :             return
     130              :          end if
     131              : 
     132            0 :          ierr = 0
     133              :          !L_expected = compute_L_face(s, k, ierr)
     134              :          !if (ierr /= 0) return
     135            0 :          L_expected = s% Lr_ad(k) + s% Lc_ad(k) + s% Lt_ad(k)
     136            0 :          L_actual = wrap_L_00(s, k)
     137            0 :          L_start_max = maxval(s% L_start(1:s% nz))
     138            0 :          scale = 1d0/L_start_max
     139            0 :          if (is_bad(scale)) then
     140            0 :             write(*,2) 'do1_rsp2_L_eqn scale', k, scale
     141            0 :             call mesa_error(__FILE__,__LINE__,'do1_rsp2_L_eqn')
     142              :          end if
     143            0 :          resid = (L_expected - L_actual)*scale
     144              : 
     145            0 :          residual = resid%val
     146            0 :          s% equ(s% i_equL, k) = residual
     147              :          if (test_partials) then
     148              :             s% solver_test_partials_val = residual
     149              :          end if
     150              : 
     151            0 :          call save_eqn_residual_info(s, k, nvar, s% i_equL, resid, 'do1_rsp2_L_eqn', ierr)
     152            0 :          if (ierr /= 0) return
     153              : 
     154              :          if (test_partials) then
     155              :             s% solver_test_partials_var = s% i_lnR
     156              :             s% solver_test_partials_dval_dx = resid%d1Array(i_lnR_00)
     157              :             write(*,4) 'do1_rsp2_L_eqn', s% solver_test_partials_var
     158              :          end if
     159            0 :       end subroutine do1_rsp2_L_eqn
     160              : 
     161              : 
     162            0 :       subroutine do1_rsp2_Hp_eqn(s, k, nvar, ierr)
     163            0 :          use star_utils, only: save_eqn_residual_info
     164              :          type (star_info), pointer :: s
     165              :          integer, intent(in) :: k, nvar
     166              :          integer, intent(out) :: ierr
     167              :          type(auto_diff_real_star_order1) ::  &
     168              :             Hp_expected, Hp_actual,resid
     169            0 :          real(dp) :: residual, Hp_start
     170              :          logical :: test_partials
     171              :          include 'formats'
     172              :          !test_partials = (k == s% solver_test_partials_k)
     173            0 :          test_partials = .false.
     174              : 
     175            0 :          if (.not. s% RSP2_flag) then
     176            0 :             ierr = -1
     177            0 :             return
     178              :          end if
     179              : 
     180              :          ierr = 0
     181            0 :          Hp_expected = Hp_face_for_rsp2_eqn(s, k, ierr)
     182            0 :          if (ierr /= 0) return
     183            0 :          Hp_actual = wrap_Hp_00(s, k)
     184            0 :          Hp_start = s% Hp_face_start(k)
     185            0 :          resid = (Hp_expected - Hp_actual)/max(Hp_expected,Hp_actual)
     186              : 
     187            0 :          residual = resid%val
     188            0 :          s% equ(s% i_equ_Hp, k) = residual
     189              :          if (test_partials) then
     190              :             s% solver_test_partials_val = residual
     191              :          end if
     192              : 
     193            0 :          if (residual > 1d3) then
     194            0 :          !$omp critical (hydro_rsp2_1)
     195            0 :             write(*,2) 'residual', k, residual
     196            0 :             write(*,2) 'Hp_expected', k, Hp_expected%val
     197            0 :             write(*,2) 'Hp_actual', k, Hp_actual%val
     198            0 :             call mesa_error(__FILE__,__LINE__,'do1_rsp2_Hp_eqn')
     199              :          !$omp end critical (hydro_rsp2_1)
     200              :          end if
     201              : 
     202            0 :          call save_eqn_residual_info(s, k, nvar, s% i_equ_Hp, resid, 'do1_rsp2_Hp_eqn', ierr)
     203            0 :          if (ierr /= 0) return
     204              : 
     205              :          if (test_partials) then
     206              :             s% solver_test_partials_var = s% i_lnR
     207              :             s% solver_test_partials_dval_dx = resid%d1Array(i_lnR_00)
     208              :             write(*,4) 'do1_rsp2_Hp_eqn', s% solver_test_partials_var
     209              :          end if
     210              : 
     211            0 :       end subroutine do1_rsp2_Hp_eqn
     212              : 
     213              : 
     214            0 :       real(dp) function Hp_face_for_rsp2_val(s, k, ierr) result(Hp_face)  ! cm
     215              :          type (star_info), pointer :: s
     216              :          integer, intent(in) :: k
     217              :          integer, intent(out) :: ierr
     218              :          type(auto_diff_real_star_order1) :: Hp_face_ad
     219              :          ierr = 0
     220            0 :          Hp_face_ad = Hp_face_for_rsp2_eqn(s, k, ierr)
     221            0 :          if (ierr /= 0) return
     222            0 :          Hp_face = Hp_face_ad%val
     223            0 :       end function Hp_face_for_rsp2_val
     224              : 
     225              : 
     226            0 :       function Hp_face_for_rsp2_eqn(s, k, ierr) result(Hp_face)  ! cm
     227              :          type (star_info), pointer :: s
     228              :          integer, intent(in) :: k
     229              :          integer, intent(out) :: ierr
     230              :          type(auto_diff_real_star_order1) :: Hp_face
     231              :          type(auto_diff_real_star_order1) :: &
     232              :             rho_face, area, dlnPeos, &
     233              :             r_00, Peos_00, d_00, Peos_m1, d_m1, Peos_div_rho, &
     234              :             d_face, Peos_face, alt_Hp_face, A
     235            0 :          real(dp) :: alfa, beta
     236              :          include 'formats'
     237            0 :          ierr = 0
     238            0 :          if (k > s% nz) then
     239            0 :             Hp_face = 1d0  ! not used
     240            0 :             return
     241              :          end if
     242            0 :          if (k > 1 .and. .not. s% RSP2_assume_HSE) then
     243            0 :             call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
     244            0 :             rho_face = alfa*wrap_d_00(s,k) + beta*wrap_d_m1(s,k)
     245            0 :             area = 4d0*pi*pow2(wrap_r_00(s,k))
     246            0 :             dlnPeos = wrap_lnPeos_m1(s,k) - wrap_lnPeos_00(s,k)
     247            0 :             Hp_face = -s% dm_bar(k)/(area*rho_face*dlnPeos)
     248              :          else
     249            0 :             r_00 = wrap_r_00(s, k)  ! not time-centered in RSP
     250            0 :             d_00 = wrap_d_00(s, k)
     251            0 :             Peos_00 = wrap_Peos_00(s, k)
     252            0 :             if (k == 1) then
     253            0 :                Peos_div_rho = Peos_00/d_00
     254            0 :                Hp_face = pow2(r_00)*Peos_div_rho/(s% cgrav(k)*s% m(k))
     255              :             else
     256            0 :                d_m1 = wrap_d_m1(s, k)
     257            0 :                Peos_m1 = wrap_Peos_m1(s, k)
     258            0 :                call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
     259            0 :                Peos_div_rho = alfa*Peos_00/d_00 + beta*Peos_m1/d_m1
     260            0 :                Hp_face = pow2(r_00)*Peos_div_rho/(s% cgrav(k)*s% m(k))
     261            0 :                if (k==-104) then
     262            0 :                   write(*,3) 'RSP2 Hp P_div_rho Pdrho_00 Pdrho_m1', k, s% solver_iter, &
     263            0 :                      Hp_face%val, Peos_div_rho%val, Peos_00%val/d_00%val, Peos_m1%val/d_m1%val
     264              :                   !write(*,3) 'RSP2 Hp r2_div_Gm r_start r', k, s% solver_iter, &
     265              :                   !   Hp_face%val, pow2(r_00%val)/(s% cgrav(k)*s% m(k)), &
     266              :                   !   s% r_start(k), r_00%val
     267              :                end if
     268            0 :                if (s% alt_scale_height_flag) then
     269            0 :                   call mesa_error(__FILE__,__LINE__,'Hp_face_for_rsp2_eqn: cannot use alt_scale_height_flag')
     270              :                   ! consider sound speed*hydro time scale as an alternative scale height
     271            0 :                   d_face = alfa*d_00 + beta*d_m1
     272            0 :                   Peos_face = alfa*Peos_00 + beta*Peos_m1
     273            0 :                   alt_Hp_face = sqrt(Peos_face/s% cgrav(k))/d_face
     274            0 :                   if (alt_Hp_face%val < Hp_face%val) then  ! blend
     275            0 :                      A = pow2(alt_Hp_face/Hp_face)  ! 0 <= A%val < 1
     276            0 :                      Hp_face = A*Hp_face + (1d0 - A)*alt_Hp_face
     277              :                   end if
     278              :                end if
     279              :             end if
     280              :          end if
     281            0 :       end function Hp_face_for_rsp2_eqn
     282              : 
     283              : 
     284            0 :       subroutine do1_turbulent_energy_eqn(s, k, nvar, ierr)
     285              :          use star_utils, only: set_energy_eqn_scal, save_eqn_residual_info
     286              :          type (star_info), pointer :: s
     287              :          integer, intent(in) :: k, nvar
     288              :          integer, intent(out) :: ierr
     289              :          ! for OLD WAY
     290              :          type(auto_diff_real_star_order1) :: &
     291              :             d_turbulent_energy_ad, Ptrb_dV_ad, dt_C_ad, dt_Eq_ad
     292              :          type(auto_diff_real_star_order1) :: w_00
     293              :          type(auto_diff_real_star_order1) :: tst, resid_ad, dt_dLt_dm_ad
     294              :          type(accurate_auto_diff_real_star_order1) :: esum_ad
     295              :          logical :: non_turbulent_cell, test_partials
     296            0 :          real(dp) :: residual, scal
     297              :          include 'formats'
     298              :          !test_partials = (k == s% solver_test_partials_k)
     299            0 :          test_partials = .false.
     300              : 
     301            0 :          ierr = 0
     302            0 :          w_00 = wrap_w_00(s,k)
     303              : 
     304              :          non_turbulent_cell = &
     305              :             s% mixing_length_alpha == 0d0 .or. &
     306              :             k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
     307            0 :             k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)
     308            0 :          if (.not. s% RSP2_flag) then
     309            0 :             resid_ad = w_00 - s% w_start(k)  ! just hold w constant when not using RSP2
     310            0 :          else if (non_turbulent_cell) then
     311            0 :             resid_ad = w_00/s% csound(k)  ! make w = 0
     312              :          else
     313            0 :             call setup_d_turbulent_energy(ierr); if (ierr /= 0) return  ! erg g^-1 = cm^2 s^-2
     314            0 :             call setup_Ptrb_dV_ad(ierr); if (ierr /= 0) return  ! erg g^-1
     315            0 :             call setup_dt_dLt_dm_ad(ierr); if (ierr /= 0) return  ! erg g^-1
     316            0 :             call setup_dt_C_ad(ierr); if (ierr /= 0) return  ! erg g^-1
     317            0 :             call setup_dt_Eq_ad(ierr); if (ierr /= 0) return  ! erg g^-1
     318            0 :             call set_energy_eqn_scal(s, k, scal, ierr); if (ierr /= 0) return  ! 1/(erg g^-1 s^-1)
     319              :             ! sum terms in esum_ad using accurate_auto_diff_real_star_order1
     320            0 :             esum_ad = d_turbulent_energy_ad + Ptrb_dV_ad + dt_dLt_dm_ad - dt_C_ad - dt_Eq_ad  ! erg g^-1
     321            0 :             resid_ad = esum_ad
     322              : 
     323            0 :             if (k==-35 .and. s% solver_iter == 1) then
     324            0 :                   write(*,3) 'RSP2 w dEt PdV dtC dtEq', k, s% solver_iter, &
     325            0 :                      w_00%val, d_turbulent_energy_ad%val, Ptrb_dV_ad%val, dt_C_ad%val, dt_Eq_ad%val
     326              :             end if
     327              : 
     328            0 :             resid_ad = resid_ad*scal/s%dt  ! to make residual unitless, must cancel out the dt in scal
     329              : 
     330              :          end if
     331              : 
     332            0 :          residual = resid_ad%val
     333            0 :          s% equ(s% i_detrb_dt, k) = residual
     334              : 
     335              :          if (test_partials) then
     336              :             tst = residual
     337              :             s% solver_test_partials_val = tst%val
     338              :             if (s% solver_iter == 12) &
     339              :                write(*,*) 'do1_turbulent_energy_eqn', s% solver_test_partials_var, s% lnd(k), tst%val
     340              :          end if
     341              : 
     342            0 :          call save_eqn_residual_info(s, k, nvar, s% i_detrb_dt, resid_ad, 'do1_turbulent_energy_eqn', ierr)
     343            0 :          if (ierr /= 0) return
     344              : 
     345            0 :          if (test_partials) then
     346              :             s% solver_test_partials_var = s% i_lnd
     347              :             s% solver_test_partials_dval_dx = tst%d1Array(i_lnd_00)     ! xi0 good , xi1 partial 0, xi2 good.  Af horrible.'
     348              :             write(*,*) 'do1_turbulent_energy_eqn', s% solver_test_partials_var, s% lnd(k)/ln10, tst%val
     349              :          end if
     350              : 
     351              :          contains
     352              : 
     353            0 :          subroutine setup_d_turbulent_energy(ierr)  ! erg g^-1
     354              :             integer, intent(out) :: ierr
     355            0 :             ierr = 0
     356            0 :             d_turbulent_energy_ad = wrap_etrb_00(s,k) - get_etrb_start(s,k)
     357            0 :          end subroutine setup_d_turbulent_energy
     358              : 
     359              :          ! Ptrb_dV_ad = Ptrb_ad*dV_ad
     360            0 :          subroutine setup_Ptrb_dV_ad(ierr)  ! erg g^-1
     361              :             use star_utils, only: calc_Ptrb_ad_tw
     362              :             integer, intent(out) :: ierr
     363              :             type(auto_diff_real_star_order1) :: Ptrb_ad, PT0, dV_ad, d_00
     364            0 :             call calc_Ptrb_ad_tw(s, k, Ptrb_ad, PT0, ierr)
     365            0 :             if (ierr /= 0) return
     366            0 :             d_00 = wrap_d_00(s,k)
     367            0 :             dV_ad = 1d0/d_00 - 1d0/s% rho_start(k)
     368            0 :             Ptrb_dV_ad = Ptrb_ad*dV_ad  ! erg cm^-3 cm^-3 g^-1 = erg g^-1
     369            0 :          end subroutine setup_Ptrb_dV_ad
     370              : 
     371            0 :          subroutine setup_dt_dLt_dm_ad(ierr)  ! erg g^-1
     372              :             integer, intent(out) :: ierr
     373              :             type(auto_diff_real_star_order1) :: Lt_00, Lt_p1
     374              :             real(dp) :: L_theta
     375              :             include 'formats'
     376            0 :             ierr = 0
     377            0 :             if (s% using_velocity_time_centering .and. &
     378              :                      s% include_L_in_velocity_time_centering) then
     379            0 :                L_theta = s% L_theta_for_velocity_time_centering
     380              :             else
     381            0 :                L_theta = 1d0
     382              :             end if
     383            0 :             Lt_00 = L_theta*s% Lt_ad(k) + (1d0 - L_theta)*s% Lt_start(k)
     384            0 :             if (k == s% nz) then
     385            0 :                Lt_p1 = 0d0
     386              :             else
     387            0 :                Lt_p1 = L_theta*shift_p1(s% Lt_ad(k+1)) + (1d0 - L_theta)*s% Lt_start(k+1)
     388            0 :                if (ierr /= 0) return
     389              :             end if
     390            0 :             dt_dLt_dm_ad = (Lt_00 - Lt_p1)*s%dt/s%dm(k)
     391            0 :          end subroutine setup_dt_dLt_dm_ad
     392              : 
     393            0 :          subroutine setup_dt_C_ad(ierr)  ! erg g^-1
     394              :             integer, intent(out) :: ierr
     395              :             type(auto_diff_real_star_order1) :: C
     396            0 :             C = s% COUPL_ad(k)  ! compute_C(s, k, ierr) ! erg g^-1 s^-1
     397            0 :             if (ierr /= 0) return
     398            0 :             dt_C_ad = s%dt*C
     399              :          end subroutine setup_dt_C_ad
     400              : 
     401            0 :          subroutine setup_dt_Eq_ad(ierr)  ! erg g^-1
     402              :             integer, intent(out) :: ierr
     403              :             type(auto_diff_real_star_order1) :: Eq_cell
     404            0 :             Eq_cell = s% Eq_ad(k)  ! compute_Eq_cell(s, k, ierr) ! erg g^-1 s^-1
     405            0 :             if (ierr /= 0) return
     406            0 :             dt_Eq_ad = s%dt*Eq_cell
     407              :          end subroutine setup_dt_Eq_ad
     408              : 
     409              :       end subroutine do1_turbulent_energy_eqn
     410              : 
     411              : 
     412            0 :       subroutine get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
     413              :          type (star_info), pointer :: s
     414              :          integer, intent(in) :: k
     415              :          real(dp), intent(out) :: alfa, beta
     416              :          ! face_value = alfa*cell_value(k) + beta*cell_value(k-1)
     417            0 :          if (k == 1) call mesa_error(__FILE__,__LINE__,'bad k==1 for get_RSP2_alfa_beta_face_weights')
     418            0 :          if (s% RSP2_use_mass_interp_face_values) then
     419            0 :             alfa = s% dq(k-1)/(s% dq(k-1) + s% dq(k))
     420            0 :             beta = 1d0 - alfa
     421              :          else
     422            0 :             alfa = 0.5d0
     423            0 :             beta = 0.5d0
     424              :          end if
     425            0 :       end subroutine get_RSP2_alfa_beta_face_weights
     426              : 
     427              : 
     428            0 :       function compute_Y_face(s, k, ierr) result(Y_face)  ! superadiabatic gradient [unitless]
     429              :          type (star_info), pointer :: s
     430              :          integer, intent(in) :: k
     431              :          integer, intent(out) :: ierr
     432              :          type(auto_diff_real_star_order1) :: Y_face
     433              :          type(auto_diff_real_star_order1) :: Hp_face, Y1, Y2, QQ_div_Cp_face, &
     434              :             r_00, d_00, Peos_00, Cp_00, T_00, chiT_00, chiRho_00, QQ_00, lnT_00, &
     435              :             r_m1, d_m1, Peos_m1, Cp_m1, T_m1, chiT_m1, chiRho_m1, QQ_m1, lnT_m1, &
     436              :             dlnT_dlnP, grad_ad_00, grad_ad_m1, grad_ad_face, dlnT, dlnP, alt_Y_face
     437            0 :          real(dp) :: dm_bar, alfa, beta
     438              :          include 'formats'
     439            0 :          ierr = 0
     440              : 
     441            0 :          if (k > s% nz) then
     442            0 :             Y_face = 0d0
     443            0 :             return
     444              :          end if
     445              : 
     446            0 :          if (k == 1 .or. s% mixing_length_alpha == 0d0) then
     447            0 :             Y_face = 0d0
     448            0 :             s% Y_face(k) = 0d0
     449            0 :             s% Y_face_ad(k) = 0d0
     450            0 :             return
     451              :          end if
     452              : 
     453            0 :          call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
     454              : 
     455            0 :          if (s% RSP2_use_RSP_eqn_for_Y_face) then
     456              : 
     457            0 :             dm_bar = s% dm_bar(k)
     458            0 :             Hp_face = wrap_Hp_00(s,k)
     459            0 :             r_00 = wrap_r_00(s, k)
     460            0 :             d_00 = wrap_d_00(s, k)
     461            0 :             Peos_00 = wrap_Peos_00(s, k)
     462            0 :             Cp_00 = wrap_Cp_00(s, k)
     463            0 :             T_00 = wrap_T_00(s, k)
     464            0 :             chiT_00 = wrap_chiT_00(s, k)
     465            0 :             chiRho_00 = wrap_chiRho_00(s, k)
     466            0 :             QQ_00 = chiT_00/(d_00*T_00*chiRho_00)
     467            0 :             lnT_00 = wrap_lnT_00(s,k)
     468              : 
     469            0 :             r_m1 = wrap_r_m1(s, k)
     470            0 :             d_m1 = wrap_d_m1(s, k)
     471            0 :             Peos_m1 = wrap_Peos_m1(s, k)
     472            0 :             Cp_m1 = wrap_Cp_m1(s, k)
     473            0 :             T_m1 = wrap_T_m1(s, k)
     474            0 :             chiT_m1 = wrap_chiT_m1(s, k)
     475            0 :             chiRho_m1 = wrap_chiRho_m1(s, k)
     476            0 :             QQ_m1 = chiT_m1/(d_m1*T_m1*chiRho_m1)
     477            0 :             lnT_m1 = wrap_lnT_m1(s,k)
     478            0 :             QQ_div_Cp_face = alfa*QQ_00/Cp_00 + beta*QQ_m1/Cp_m1
     479              :             ! QQ units (g cm^-3 K)^-1 = g^-1 cm^3 K^-1
     480              :             ! Cp units erg g^-1 K^-1 = g cm^2 s^-2 g^-1 K^-1 = cm^2 s^-2 K^-1
     481              :             ! QQ/Cp units = (g^-1 cm^3 K^-1)/(cm^2 s^-2 K^-1)
     482              :             !  = g^-1 cm^3 K^-1 cm^-2 s^2 K
     483              :             !  = g^-1 cm s^2
     484              :             ! P units = erg cm^-3 = g cm^2 s^-2 cm^-3 = g cm^-1 s^-2
     485              :             ! QQ/Cp*P is unitless.
     486              : 
     487            0 :             Y1 = QQ_div_Cp_face*(Peos_m1 - Peos_00) - (lnT_m1 - lnT_00)
     488              :             ! Y1 unitless
     489              : 
     490            0 :             Y2 = 4d0*pi*pow2(r_00)*Hp_face*2d0/(1d0/d_00 + 1d0/d_m1)/dm_bar
     491              :             ! units = cm^2 cm / (cm^3 g^-1) / g
     492              :             !       = cm^2 cm cm^-3 g g^-1 = unitless
     493              : 
     494            0 :             Y_face = Y1*Y2  ! unitless
     495              : 
     496            0 :             if (k==-35) then
     497            0 :                write(*,3) 'RSP2 Y_face Y1 Y2', k, s% solver_iter, s% Y_face(k), Y1%val, Y2%val
     498            0 :                write(*,3) 'Peos', k, s% solver_iter, Peos_00%val
     499            0 :                write(*,3) 'Peos', k-1, s% solver_iter, Peos_m1%val
     500            0 :                write(*,3) 'QQ', k, s% solver_iter, QQ_00%val
     501            0 :                write(*,3) 'QQ', k-1, s% solver_iter, QQ_m1%val
     502            0 :                write(*,3) 'Cp', k, s% solver_iter, Cp_00%val
     503            0 :                write(*,3) 'Cp', k-1, s% solver_iter, Cp_m1%val
     504            0 :                write(*,3) 'lgT', k, s% solver_iter, lnT_00%val/ln10
     505            0 :                write(*,3) 'lgT', k-1, s% solver_iter, lnT_m1%val/ln10
     506            0 :                write(*,3) 'lgd', k, s% solver_iter, s% lnd(k)/ln10
     507            0 :                write(*,3) 'lgd', k-1, s% solver_iter, s% lnd(k-1)/ln10
     508              :                !call mesa_error(__FILE__,__LINE__,'compute_Y_face')
     509              :             end if
     510              : 
     511              :          else
     512              : 
     513            0 :             grad_ad_00 = wrap_grad_ad_00(s,k)
     514            0 :             grad_ad_m1 = wrap_grad_ad_m1(s,k)
     515            0 :             grad_ad_face = alfa*grad_ad_00 + beta*grad_ad_m1
     516            0 :             dlnT = wrap_lnT_m1(s,k) - wrap_lnT_00(s,k)
     517            0 :             dlnP = wrap_lnPeos_m1(s,k) - wrap_lnPeos_00(s,k)
     518            0 :             dlnT_dlnP = dlnT/dlnP
     519            0 :             if (is_bad(dlnT_dlnP%val)) then
     520            0 :                alt_Y_face = 0d0
     521            0 :             else if (s% use_Ledoux_criterion .and. s% calculate_Brunt_B) then
     522              :                ! gradL = grada + gradL_composition_term
     523            0 :                alt_Y_face = dlnT_dlnP - (grad_ad_face + s% gradL_composition_term(k))
     524              :             else
     525            0 :                alt_Y_face = dlnT_dlnP - grad_ad_face
     526              :             end if
     527            0 :             if (is_bad(alt_Y_face%val)) alt_Y_face = 0
     528            0 :             Y_face = alt_Y_face
     529              : 
     530              :          end if
     531              : 
     532            0 :          s% Y_face_ad(k) = Y_face
     533            0 :          s% Y_face(k) = Y_face%val
     534              : 
     535            0 :       end function compute_Y_face
     536              : 
     537              : 
     538            0 :       function compute_PII_face(s, k, ierr) result(PII_face)  ! ergs g^-1 K^-1 (like Cp)
     539              :          type (star_info), pointer :: s
     540              :          integer, intent(in) :: k
     541              :          type(auto_diff_real_star_order1) :: PII_face
     542              :          integer, intent(out) :: ierr
     543              :          type(auto_diff_real_star_order1) :: Cp_00, Cp_m1, Cp_face, Y_face, T_00, T_m1
     544              :          type(auto_diff_real_star_order1) :: X, FL, scale, T_face, e_face, Peos_face, rho_face, h_face
     545            0 :          real(dp) :: ALFAS_ALFA, alfa, beta
     546              :          include 'formats'
     547            0 :          ierr = 0
     548            0 :          if (k > s% nz) then
     549            0 :             PII_face = 0d0
     550            0 :             return
     551              :          end if
     552            0 :          if (k == 1 .or. s% mixing_length_alpha == 0d0 .or. &
     553              :                k == s% nz) then  ! just skip k == nz to be like RSP
     554            0 :             PII_face = 0d0
     555            0 :             s% PII(k) = 0d0
     556            0 :             s% PII_ad(k) = 0d0
     557            0 :             return
     558              :          end if
     559            0 :          Y_face = s% Y_face_ad(k)  ! compute_Y_face(s, k, ierr)
     560            0 :          if (ierr /= 0) return
     561            0 :          Cp_00 = wrap_Cp_00(s, k)
     562            0 :          Cp_m1 = wrap_Cp_m1(s, k)
     563            0 :          T_00= wrap_T_00(s, k)
     564            0 :          T_m1 = wrap_T_m1(s, k)
     565            0 :          call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
     566            0 :          Cp_face = alfa*Cp_00 + beta*Cp_m1  ! ergs g^-1 K^-1
     567            0 :          T_face = alfa*Cp_00 + beta*Cp_m1
     568            0 :          rho_face = alfa*wrap_d_00(s,k) + beta*wrap_d_m1(s,k)
     569            0 :          Peos_face = alfa*wrap_Peos_00(s,k) + beta*wrap_Peos_m1(s,k)
     570            0 :          e_face = alfa*wrap_e_00(s,k) + beta*wrap_e_m1(s,k)
     571            0 :          h_face = e_face + Peos_face/rho_face
     572            0 :          ALFAS_ALFA = x_ALFAS*s% mixing_length_alpha
     573            0 :          PII_face = ALFAS_ALFA*Cp_face*Y_face
     574              : 
     575            0 :          scale = 1d0
     576            0 :          if (Y_face > 0d0 .and. s% use_TDC_enthalpy_flux_limiter) then
     577              :             ! X = G/F
     578            0 :             X = (Cp_face*T_face/h_face)*ALFAS_ALFA* Y_face / sqrt_2_div_3
     579            0 :             FL = flux_limiter_function(X)
     580              :             ! Avoid 0/0 or tiny/tiny; for X ≈ 0, FL ≈ X so scale ~ 1 anyway.
     581            0 :             if (abs(X%val) >= 0.95d0) then
     582            0 :                scale = FL / X
     583              :             else
     584            0 :                scale = 1d0
     585              :             end if
     586              :          end if
     587              : 
     588            0 :          s% PII(k) = PII_face%val*scale%val
     589            0 :          s% PII_ad(k) = PII_face*scale
     590            0 :          if (k == -2 .and. s% PII(k) < 0d0) then
     591            0 :             write(*,2) 's% PII(k)', k, s% PII(k)
     592            0 :             write(*,2) 'Cp_face', k, Cp_face%val
     593            0 :             write(*,2) 'Y_face', k, Y_face%val
     594              :             !write(*,2) 'PII_face%val', k, PII_face%val
     595              :             !write(*,2) 'T_rho_face%val', k, T_rho_face%val
     596              :             !write(*,2) '', k,
     597              :             !write(*,2) '', k,
     598            0 :             call mesa_error(__FILE__,__LINE__,'compute_PII_face')
     599              :          end if
     600            0 :       end function compute_PII_face
     601              : 
     602            0 :       type(auto_diff_real_star_order1) function flux_limiter_function(X) result(FL) ! should be c2 continuous
     603              :         type(auto_diff_real_star_order1), intent(in) :: X
     604              :         real(dp), parameter :: X0    = 0.95_dp         ! start of transition
     605              :         real(dp), parameter :: delta = 0.05_dp         ! width of transition
     606              :         real(dp), parameter :: X1    = 1d0 !X0 + delta      ! end of transition
     607              : 
     608              :         type(auto_diff_real_star_order1) :: s, p
     609              : 
     610              :         ! Region 1: purely linear, FL = X
     611            0 :         if (X%val < X0) then ! should not be encountered
     612            0 :            FL = X
     613              : 
     614              :         ! Region 3: saturated, FL = 1
     615            0 :         else if (X%val >= X1) then
     616            0 :            FL = 1.0_dp
     617              : 
     618              :         ! Region 2: smooth C² transition between the two
     619              :         else
     620              :            ! Normalized coordinate in [0,1]
     621            0 :            s = (X - X0) / (X1 - X0)
     622              : 
     623              :            ! Quintic "smootherstep" polynomial:
     624              :            ! p(s) = 10 s^3 - 15 s^4 + 6 s^5
     625              :            ! p(0)=0, p(1)=1, p'(0)=p'(1)=0, p''(0)=p''(1)=0
     626            0 :            p = pow3(s) * (10.0_dp + s * (-15.0_dp + 6.0_dp * s))
     627              : 
     628              :            ! Blend between line FL=X and flat FL=1
     629              :            ! At s=0:  FL = X
     630              :            ! At s=1:  FL = 1
     631              :            ! Because p', p'' vanish at 0 and 1, FL, FL', FL'' all match.
     632            0 :            FL = X + (1.0_dp - X) * p
     633              :         end if
     634            0 :       end function flux_limiter_function
     635              : 
     636            0 :       function compute_d_v_div_r(s, k, ierr) result(d_v_div_r)  ! s^-1
     637              :          type (star_info), pointer :: s
     638              :          integer, intent(in) :: k
     639              :          type(auto_diff_real_star_order1) :: d_v_div_r
     640              :          integer, intent(out) :: ierr
     641              :          type(auto_diff_real_star_order1) :: v_00, v_p1, r_00, r_p1
     642              :          include 'formats'
     643            0 :          ierr = 0
     644            0 :          v_00 = wrap_v_00(s,k)
     645            0 :          v_p1 = wrap_v_p1(s,k)
     646            0 :          r_00 = wrap_r_00(s,k)
     647            0 :          r_p1 = wrap_r_p1(s,k)
     648            0 :          if (r_p1%val == 0d0) r_p1 = 1d0
     649            0 :          d_v_div_r = v_00/r_00 - v_p1/r_p1  ! units s^-1
     650            0 :       end function compute_d_v_div_r
     651              : 
     652              : 
     653            0 :       function compute_d_v_div_r_opt_time_center(s, k, ierr) result(d_v_div_r)  ! s^-1
     654              :          type (star_info), pointer :: s
     655              :          integer, intent(in) :: k
     656              :          type(auto_diff_real_star_order1) :: d_v_div_r
     657              :          integer, intent(out) :: ierr
     658              :          type(auto_diff_real_star_order1) :: v_00, v_p1, r_00, r_p1
     659              :          include 'formats'
     660            0 :          ierr = 0
     661            0 :          v_00 = wrap_opt_time_center_v_00(s,k)
     662            0 :          v_p1 = wrap_opt_time_center_v_p1(s,k)
     663            0 :          r_00 = wrap_opt_time_center_r_00(s,k)
     664            0 :          r_p1 = wrap_opt_time_center_r_p1(s,k)
     665            0 :          if (r_p1%val == 0d0) r_p1 = 1d0
     666            0 :          d_v_div_r = v_00/r_00 - v_p1/r_p1  ! units s^-1
     667            0 :       end function compute_d_v_div_r_opt_time_center
     668              : 
     669              : 
     670            0 :       function wrap_Hp_cell(s, k) result(Hp_cell)  ! cm
     671              :          type (star_info), pointer :: s
     672              :          integer, intent(in) :: k
     673              :          type(auto_diff_real_star_order1) :: Hp_cell
     674            0 :          Hp_cell = 0.5d0*(wrap_Hp_00(s,k) + wrap_Hp_p1(s,k))
     675            0 :       end function wrap_Hp_cell
     676              : 
     677              : 
     678            0 :       function Hp_cell_for_Chi(s, k, ierr) result(Hp_cell)  ! cm
     679              :          type (star_info), pointer :: s
     680              :          integer, intent(in) :: k
     681              :          integer, intent(out) :: ierr
     682              :          type(auto_diff_real_star_order1) :: Hp_cell
     683              :          type(auto_diff_real_star_order1) :: d_00, Peos_00, rmid
     684            0 :          real(dp) :: mmid, cgrav_mid
     685              :          include 'formats'
     686            0 :          ierr = 0
     687              : 
     688            0 :          Hp_cell = wrap_Hp_cell(s, k)
     689            0 :          return
     690              : 
     691              :          d_00 = wrap_d_00(s, k)
     692              :          Peos_00 = wrap_Peos_00(s, k)
     693              :          if (k < s% nz) then
     694              :             rmid = 0.5d0*(wrap_r_00(s,k) + wrap_r_p1(s,k))
     695              :             mmid = 0.5d0*(s% m(k) + s% m(k+1))
     696              :             cgrav_mid = 0.5d0*(s% cgrav(k) + s% cgrav(k+1))
     697              :          else
     698              :             rmid = 0.5d0*(wrap_r_00(s,k) + s% r_center)
     699              :             mmid = 0.5d0*(s% m(k) + s% m_center)
     700              :             cgrav_mid = s% cgrav(k)
     701              :          end if
     702              :          Hp_cell = pow2(rmid)*Peos_00/(d_00*cgrav_mid*mmid)
     703              :          if (s% alt_scale_height_flag) then
     704              :             call mesa_error(__FILE__,__LINE__,'Hp_cell_for_Chi: cannot use alt_scale_height_flag')
     705              :          end if
     706              :       end function Hp_cell_for_Chi
     707              : 
     708              : 
     709            0 :       function compute_Chi_cell(s, k, ierr) result(Chi_cell)
     710              :          ! eddy viscosity energy (Kuhfuss 1986) [erg]
     711              :          type (star_info), pointer :: s
     712              :          integer, intent(in) :: k
     713              :          type(auto_diff_real_star_order1) :: Chi_cell
     714              :          integer, intent(out) :: ierr
     715              :          type(auto_diff_real_star_order1) :: &
     716              :             rho2, r6_cell, d_v_div_r, Hp_cell, w_00, d_00, r_00, r_p1
     717            0 :          real(dp) :: f, ALFAM_ALFA
     718              :          include 'formats'
     719            0 :          ierr = 0
     720            0 :          ALFAM_ALFA = s% RSP2_alfam*s% mixing_length_alpha
     721              :          if (ALFAM_ALFA == 0d0 .or. &
     722            0 :                k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
     723              :                k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
     724            0 :             Chi_cell = 0d0
     725            0 :             if (k >= 1 .and. k <= s% nz) then
     726            0 :                s% Chi(k) = 0d0
     727            0 :                s% Chi_ad(k) = 0d0
     728              :             end if
     729              :          else
     730            0 :             Hp_cell = Hp_cell_for_Chi(s, k, ierr)
     731            0 :             if (ierr /= 0) return
     732            0 :             d_v_div_r = compute_d_v_div_r(s, k, ierr)
     733            0 :             if (ierr /= 0) return
     734            0 :             w_00 = wrap_w_00(s,k)
     735            0 :             d_00 = wrap_d_00(s,k)
     736            0 :             f = (16d0/3d0)*pi*ALFAM_ALFA/s% dm(k)
     737            0 :             rho2 = pow2(d_00)
     738            0 :             r_00 = wrap_r_00(s,k)
     739            0 :             r_p1 = wrap_r_p1(s,k)
     740            0 :             r6_cell = 0.5d0*(pow6(r_00) + pow6(r_p1))
     741            0 :             Chi_cell = f*rho2*r6_cell*d_v_div_r*Hp_cell*w_00
     742              :             ! units = g^-1 cm s^-1 g^2 cm^-6 cm^6 s^-1 cm
     743              :             !       = g cm^2 s^-2
     744              :             !       = erg
     745              :          end if
     746            0 :          s% Chi(k) = Chi_cell%val
     747            0 :          s% Chi_ad(k) = Chi_cell
     748              : 
     749            0 :       end function compute_Chi_cell
     750              : 
     751              : 
     752            0 :       function compute_Eq_cell(s, k, ierr) result(Eq_cell)  ! erg g^-1 s^-1
     753              :          type (star_info), pointer :: s
     754              :          integer, intent(in) :: k
     755              :          type(auto_diff_real_star_order1) :: Eq_cell
     756              :          integer, intent(out) :: ierr
     757              :          type(auto_diff_real_star_order1) :: d_v_div_r, Chi_cell
     758              :          include 'formats'
     759            0 :          ierr = 0
     760              :          if (s% mixing_length_alpha == 0d0 .or. &
     761            0 :              k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
     762              :              k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
     763            0 :             Eq_cell = 0d0
     764            0 :             if (k >= 1 .and. k <= s% nz) s% Eq_ad(k) = 0d0
     765              :          else
     766            0 :             Chi_cell = s% Chi_ad(k)  ! compute_Chi_cell(s,k,ierr)
     767            0 :             if (ierr /= 0) return
     768            0 :             d_v_div_r = compute_d_v_div_r_opt_time_center(s, k, ierr)
     769            0 :             if (ierr /= 0) return
     770            0 :             Eq_cell = 4d0*pi*Chi_cell*d_v_div_r/s% dm(k)  ! erg s^-1 g^-1
     771              :          end if
     772            0 :          s% Eq(k) = Eq_cell%val
     773            0 :          s% Eq_ad(k) = Eq_cell
     774            0 :       end function compute_Eq_cell
     775              : 
     776              : 
     777            0 :       function compute_Uq_face(s, k, ierr) result(Uq_face)  ! cm s^-2, acceleration
     778              :          type (star_info), pointer :: s
     779              :          integer, intent(in) :: k
     780              :          type(auto_diff_real_star_order1) :: Uq_face
     781              :          integer, intent(out) :: ierr
     782              :          type(auto_diff_real_star_order1) :: Chi_00, Chi_m1, r_00
     783              :          include 'formats'
     784            0 :          ierr = 0
     785              :          if (s% mixing_length_alpha == 0d0 .or. &
     786            0 :              k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
     787              :              k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
     788            0 :             Uq_face = 0d0
     789              :          else
     790            0 :             r_00 = wrap_opt_time_center_r_00(s,k)
     791            0 :             Chi_00 = s% Chi_ad(k)  ! compute_Chi_cell(s,k,ierr)
     792            0 :             if (k > 1) then
     793              :                !Chi_m1 = shift_m1(compute_Chi_cell(s,k-1,ierr))
     794            0 :                Chi_m1 = shift_m1(s% Chi_ad(k-1))
     795            0 :                if (ierr /= 0) return
     796              :             else
     797            0 :                Chi_m1 = 0d0
     798              :             end if
     799            0 :             Uq_face = 4d0*pi*(Chi_m1 - Chi_00)/(r_00*s% dm_bar(k))
     800              : 
     801            0 :             if (k==-56) then
     802            0 :                write(*,3) 'RSP2 Uq chi_m1 chi_00 r', k, s% solver_iter, &
     803            0 :                   Uq_face%val, Chi_m1%val, Chi_00%val, r_00%val
     804              :             end if
     805              : 
     806              :          end if
     807              :          ! erg g^-1 cm^-1 = g cm^2 s^-2 g^-1 cm^-1 = cm s^-2, acceleration
     808            0 :          s% Uq(k) = Uq_face%val
     809            0 :       end function compute_Uq_face
     810              : 
     811              : 
     812            0 :       function compute_Source(s, k, ierr) result(Source)  ! erg g^-1 s^-1
     813              :          type (star_info), pointer :: s
     814              :          integer, intent(in) :: k
     815              :          type(auto_diff_real_star_order1) :: Source
     816              :          ! source_div_w assumes RSP2_source_seed == 0
     817              :          integer, intent(out) :: ierr
     818              :          type(auto_diff_real_star_order1) :: &
     819              :             w_00, T_00, d_00, Peos_00, Cp_00, chiT_00, chiRho_00, QQ_00, &
     820              :             Hp_face_00, Hp_face_p1, PII_face_00, PII_face_p1, PII_div_Hp_cell, &
     821              :             P_QQ_div_Cp
     822              :          include 'formats'
     823            0 :          ierr = 0
     824            0 :          w_00 = wrap_w_00(s, k)
     825            0 :          T_00 = wrap_T_00(s, k)
     826            0 :          d_00 = wrap_d_00(s, k)
     827            0 :          Peos_00 = wrap_Peos_00(s, k)
     828            0 :          Cp_00 = wrap_Cp_00(s, k)
     829            0 :          chiT_00 = wrap_chiT_00(s, k)
     830            0 :          chiRho_00 = wrap_chiRho_00(s, k)
     831            0 :          QQ_00 = chiT_00/(d_00*T_00*chiRho_00)
     832              : 
     833            0 :          Hp_face_00 = wrap_Hp_00(s,k)
     834            0 :          PII_face_00 = s% PII_ad(k)  ! compute_PII_face(s, k, ierr)
     835            0 :          if (ierr /= 0) return
     836              : 
     837            0 :          if (k == s% nz) then
     838            0 :             PII_div_Hp_cell = PII_face_00/Hp_face_00
     839              :          else
     840            0 :             Hp_face_p1 = wrap_Hp_p1(s,k)
     841            0 :             if (ierr /= 0) return
     842              :             !PII_face_p1 = shift_p1(compute_PII_face(s, k+1, ierr))
     843            0 :             PII_face_p1 = shift_p1(s% PII_ad(k+1))
     844            0 :             if (ierr /= 0) return
     845            0 :             PII_div_Hp_cell = 0.5d0*(PII_face_00/Hp_face_00 + PII_face_p1/Hp_face_p1)
     846              :          end if
     847              : 
     848              :          ! Peos_00*QQ_00/Cp_00 = grad_ad if all perfect.
     849              :          !grad_ad_00 = wrap_grad_ad_00(s, k)
     850            0 :          P_QQ_div_Cp = Peos_00*QQ_00/Cp_00  ! use this to be same as RSP
     851            0 :          Source = (w_00 + s% RSP2_source_seed)*PII_div_Hp_cell*T_00*P_QQ_div_Cp
     852              : 
     853              :          ! PII units same as Cp = erg g^-1 K^-1
     854              :          ! P*QQ/Cp is unitless (see Y_face)
     855              :          ! Source units = (erg g^-1 K^-1) cm^-1 cm s^-1 K
     856              :          !     = erg g^-1 s^-1
     857              : 
     858            0 :          if (k==-109) then
     859            0 :             write(*,3) 'RSP2 Source w PII_div_Hp T_P_QQ_div_Cp', k, s% solver_iter, &
     860            0 :                Source%val, w_00%val, PII_div_Hp_cell%val, T_00%val*P_QQ_div_Cp% val
     861              :             !write(*,3) 'RSP2 PII_00 PII_p1 Hp_00 Hp_p1', k, s% solver_iter, &
     862              :             !   PII_face_00%val, PII_face_p1%val, Hp_face_00%val, Hp_face_p1%val
     863              :          end if
     864            0 :          s% SOURCE(k) = Source%val
     865              : 
     866            0 :       end function compute_Source
     867              : 
     868              : 
     869            0 :       function compute_D(s, k, ierr) result(D)  ! erg g^-1 s^-1
     870              :          type (star_info), pointer :: s
     871              :          integer, intent(in) :: k
     872              :          type(auto_diff_real_star_order1) :: D
     873              :          type(auto_diff_real_star_order1) :: dw3, w_00
     874              :          integer, intent(out) :: ierr
     875              :          type(auto_diff_real_star_order1) :: Hp_cell
     876              :          include 'formats'
     877            0 :          ierr = 0
     878            0 :          if (s% mixing_length_alpha == 0d0) then
     879            0 :             D = 0d0
     880              :          else
     881            0 :             Hp_cell = wrap_Hp_cell(s,k)
     882            0 :             w_00 = wrap_w_00(s,k)
     883            0 :             dw3 = pow3(w_00) - pow3(s% RSP2_w_min_for_damping)
     884            0 :             D = (s% RSP2_alfad*x_CEDE/s% mixing_length_alpha)*dw3/Hp_cell
     885              :             ! units cm^3 s^-3 cm^-1 = cm^2 s^-3 = erg g^-1 s^-1
     886              :          end if
     887            0 :          if (k==-50) then
     888            0 :             write(*,3) 'RSP2 DAMP w Hp_cell dw3', k, s% solver_iter, &
     889            0 :                D%val, w_00%val, Hp_cell%val, dw3% val
     890              :          end if
     891            0 :          s% DAMP(k) = D%val
     892            0 :       end function compute_D
     893              : 
     894              : 
     895            0 :       function compute_Dr(s, k, ierr) result(Dr)  ! erg g^-1 s^-1 = cm^2 s^-3
     896              :          type (star_info), pointer :: s
     897              :          integer, intent(in) :: k
     898              :          type(auto_diff_real_star_order1) :: Dr
     899              :          integer, intent(out) :: ierr
     900              :          type(auto_diff_real_star_order1) :: &
     901              :             w_00, T_00, d_00, Cp_00, kap_00, Hp_cell, POM2
     902            0 :          real(dp) :: gammar, alpha, POM
     903              :          include 'formats'
     904            0 :          ierr = 0
     905            0 :          alpha = s% mixing_length_alpha
     906            0 :          gammar = s% RSP2_alfar*x_GAMMAR
     907            0 :          if (gammar == 0d0) then
     908            0 :             Dr = 0d0
     909            0 :             s% DAMPR(k) = 0d0
     910            0 :             return
     911              :          end if
     912            0 :          w_00 = wrap_w_00(s,k)
     913            0 :          T_00 = wrap_T_00(s,k)
     914            0 :          d_00 = wrap_d_00(s,k)
     915            0 :          Cp_00 = wrap_Cp_00(s,k)
     916            0 :          kap_00 = wrap_kap_00(s,k)
     917            0 :          Hp_cell = wrap_Hp_cell(s,k)
     918            0 :          POM = 4d0*boltz_sigma*pow2(gammar/alpha)  ! erg cm^-2 K^-4 s^-1
     919            0 :          POM2 = pow3(T_00)/(pow2(d_00)*Cp_00*kap_00)
     920              :             ! K^3 / ((g cm^-3)^2 (erg g^-1 K^-1) (cm^2 g^-1))
     921              :             ! K^3 / (cm^-4 erg K^-1) = K^4 cm^4 erg^-1
     922            0 :          Dr = get_etrb(s,k)*POM*POM2/pow2(Hp_cell)
     923              :          ! (erg cm^-2 K^-4 s^-1) (K^4 cm^4 erg^-1) cm^2 s^-2 cm^-2
     924              :          ! cm^2 s^-3 = erg g^-1 s^-1
     925            0 :          s% DAMPR(k) = Dr%val
     926            0 :       end function compute_Dr
     927              : 
     928              : 
     929            0 :       function compute_C(s, k, ierr) result(C)  ! erg g^-1 s^-1
     930              :          type (star_info), pointer :: s
     931              :          integer, intent(in) :: k
     932              :          type(auto_diff_real_star_order1) :: C
     933              :          integer, intent(out) :: ierr
     934              :          type(auto_diff_real_star_order1) :: Source, D, Dr
     935              :          if (s% mixing_length_alpha == 0d0 .or. &
     936            0 :              k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
     937              :              k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
     938            0 :             if (k >= 1 .and. k <= s% nz) then
     939            0 :                s% SOURCE(k) = 0d0
     940            0 :                s% DAMP(k) = 0d0
     941            0 :                s% DAMPR(k) = 0d0
     942            0 :                s% COUPL(k) = 0d0
     943            0 :                s% COUPL_ad(k) = 0d0
     944              :             end if
     945            0 :             C = 0d0
     946            0 :             return
     947              :          end if
     948            0 :          Source = compute_Source(s, k, ierr)
     949            0 :          if (ierr /= 0) return
     950            0 :          D = compute_D(s, k, ierr)
     951            0 :          if (ierr /= 0) return
     952            0 :          Dr = compute_Dr(s, k, ierr)
     953            0 :          if (ierr /= 0) return
     954            0 :          C = Source - D - Dr
     955            0 :          s% COUPL(k) = C%val
     956            0 :          s% COUPL_ad(k) = C
     957            0 :       end function compute_C
     958              : 
     959              : 
     960            0 :       function compute_L_face(s, k, ierr) result(L_face)  ! erg s^-1
     961              :          type (star_info), pointer :: s
     962              :          integer, intent(in) :: k
     963              :          type(auto_diff_real_star_order1) :: L_face
     964              :          integer, intent(out) :: ierr
     965              :          type(auto_diff_real_star_order1) :: Lr, Lc, Lt
     966            0 :          call compute_L_terms(s, k, L_face, Lr, Lc, Lt, ierr)
     967            0 :       end function compute_L_face
     968              : 
     969              : 
     970            0 :       subroutine compute_L_terms(s, k, L, Lr, Lc, Lt, ierr)
     971              :          type (star_info), pointer, intent(in) :: s
     972              :          integer, intent(in) :: k
     973              :          type(auto_diff_real_star_order1), intent(out) :: L, Lr, Lc, Lt
     974              :          integer, intent(out) :: ierr
     975              :          include 'formats'
     976            0 :          ierr = 0
     977            0 :          if (k > s% nz) then
     978            0 :             L = 0d0
     979            0 :             L%val = s% L_center
     980            0 :             Lr = 0d0
     981            0 :             Lc = 0d0
     982            0 :             Lt = 0d0
     983            0 :             return
     984              :          end if
     985            0 :          Lr = compute_Lr(s, k, ierr)
     986            0 :          if (ierr /= 0) return
     987            0 :          if (k == 1) then
     988            0 :             Lc = 0d0
     989            0 :             Lt = 0d0
     990              :          else
     991            0 :             Lc = compute_Lc(s, k, ierr)
     992            0 :             if (ierr /= 0) return
     993            0 :             Lt = compute_Lt(s, k, ierr)
     994            0 :             if (ierr /= 0) return
     995              :          end if
     996            0 :          L = Lr + Lc + Lt
     997            0 :          s% Lr_ad(k) = Lr
     998            0 :          s% Lc_ad(k) = Lc
     999            0 :          s% Lt_ad(k) = Lt
    1000              :       end subroutine compute_L_terms
    1001              : 
    1002              : 
    1003            0 :       function compute_Lr(s, k, ierr) result(Lr)  ! erg s^-1
    1004              :          type (star_info), pointer :: s
    1005              :          integer, intent(in) :: k
    1006              :          type(auto_diff_real_star_order1) :: Lr
    1007              :          integer, intent(out) :: ierr
    1008              :          type(auto_diff_real_star_order1) :: &
    1009              :             r_00, area, T_00, T400, Erad, T_m1, T4m1, &
    1010              :             kap_00, kap_m1, kap_face, diff_T4_div_kap, BW, BK
    1011            0 :          real(dp) :: alfa
    1012              :          include 'formats'
    1013            0 :          ierr = 0
    1014            0 :          if (k > s% nz) then
    1015            0 :             Lr = s% L_center
    1016              :          else
    1017            0 :             r_00 = wrap_r_00(s,k)  ! not time centered
    1018            0 :             area = 4d0*pi*pow2(r_00)
    1019            0 :             T_00 = wrap_T_00(s,k)
    1020            0 :             T400 = pow4(T_00)
    1021            0 :             if (k == 1) then  ! Lr(1) proportional to Erad in cell(1)
    1022            0 :                Erad = crad * T400
    1023            0 :                Lr = s% RSP2_Lsurf_factor * area * clight * Erad
    1024            0 :                s% Lr(k) = Lr%val
    1025            0 :                return
    1026              :             end if
    1027            0 :             T_m1 = wrap_T_m1(s,k)
    1028            0 :             T4m1 = pow4(T_m1)
    1029            0 :             alfa = s% dq(k-1)/(s% dq(k-1) + s% dq(k))
    1030            0 :             kap_00 = wrap_kap_00(s,k)
    1031            0 :             kap_m1 = wrap_kap_m1(s,k)
    1032            0 :             kap_face = alfa*kap_00 + (1d0 - alfa)*kap_m1
    1033            0 :             diff_T4_div_kap = (T4m1 - T400)/kap_face
    1034              : 
    1035            0 :             if (s% RSP2_use_Stellingwerf_Lr) then  ! RSP style
    1036            0 :                BW = log(T4m1/T400)
    1037            0 :                if (abs(BW%val) > 1d-20) then
    1038            0 :                   BK = log(kap_m1/kap_00)
    1039            0 :                   if (abs(1d0 - BK%val/BW%val) > 1d-15 .and. abs(BW%val - BK%val) > 1d-15) then
    1040            0 :                      diff_T4_div_kap = (T4m1/kap_m1 - T400/kap_00)/(1d0 - BK/BW)
    1041              :                   end if
    1042              :                end if
    1043              :             end if
    1044            0 :             Lr = -crad*clight/3d0*diff_T4_div_kap*pow2(area)/s% dm_bar(k)
    1045              :             ! units (erg cm^-3 K^-4) (cm s^-1) (K^4 cm^-2 g cm^4) g^-1 = erg s^-1
    1046              : 
    1047              :             !s% xtra1_array(k) = s% T_start(k)
    1048              :             !s% xtra2_array(k) = T4m1%val - T400%val
    1049              :             !s% xtra3_array(k) = kap_face%val
    1050              :             !s% xtra4_array(k) = diff_T4_div_kap%val
    1051              :             !s% xtra5_array(k) = Lr%val/Lsun
    1052              :             !s% xtra6_array(k) = 1
    1053              : 
    1054              :          end if
    1055            0 :          s% Lr(k) = Lr%val
    1056            0 :       end function compute_Lr
    1057              : 
    1058              : 
    1059            0 :       function compute_Lc(s, k, ierr) result(Lc)  ! erg s^-1
    1060              :          type (star_info), pointer :: s
    1061              :          integer, intent(in) :: k
    1062              :          type(auto_diff_real_star_order1) :: Lc
    1063              :          integer, intent(out) :: ierr
    1064              :          type(auto_diff_real_star_order1) :: Lc_div_w_face
    1065            0 :          Lc = compute_Lc_terms(s, k, Lc_div_w_face, ierr)
    1066            0 :          s% Lc(k) = Lc%val
    1067            0 :       end function compute_Lc
    1068              : 
    1069              : 
    1070            0 :       function compute_Lc_terms(s, k, Lc_div_w_face, ierr) result(Lc)
    1071              :          type (star_info), pointer :: s
    1072              :          integer, intent(in) :: k
    1073              :          type(auto_diff_real_star_order1) :: Lc, Lc_div_w_face
    1074              :          integer, intent(out) :: ierr
    1075              :          type(auto_diff_real_star_order1) :: r_00, area, &
    1076              :             T_m1, T_00, d_m1, d_00, w_m1, w_00, T_rho_face, PII_face, w_face
    1077            0 :          real(dp) :: ALFAC, ALFAS, alfa, beta
    1078              :          include 'formats'
    1079            0 :          ierr = 0
    1080              :          if (s% mixing_length_alpha == 0d0 .or. &
    1081            0 :              k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
    1082              :              k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
    1083            0 :             Lc = 0d0
    1084            0 :             Lc_div_w_face = 1
    1085            0 :             return
    1086              :          end if
    1087            0 :          r_00 = wrap_r_00(s, k)
    1088            0 :          area = 4d0*pi*pow2(r_00)
    1089            0 :          T_m1 = wrap_T_m1(s, k)
    1090            0 :          T_00 = wrap_T_00(s, k)
    1091            0 :          d_m1 = wrap_d_m1(s, k)
    1092            0 :          d_00 = wrap_d_00(s, k)
    1093            0 :          w_m1 = wrap_w_m1(s, k)
    1094            0 :          w_00 = wrap_w_00(s, k)
    1095            0 :          call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
    1096            0 :          T_rho_face = alfa*T_00*d_00 + beta*T_m1*d_m1
    1097            0 :          PII_face = s% PII_ad(k)  ! compute_PII_face(s, k, ierr)
    1098            0 :          w_face = alfa*w_00 + beta*w_m1
    1099            0 :          ALFAC = x_ALFAC
    1100            0 :          ALFAS = x_ALFAS
    1101            0 :          Lc_div_w_face = area*(ALFAC/ALFAS)*T_rho_face*PII_face
    1102              :          ! units = cm^2 K g cm^-3 ergs g^-1 K^-1 = ergs cm^-1
    1103            0 :          Lc = w_face*Lc_div_w_face
    1104              :          ! units = cm s^-1 ergs cm^-1 = ergs s^-1
    1105            0 :          if (k == -458) then
    1106            0 :             write(*,2) 'Lc%val', k, Lc%val
    1107            0 :             write(*,2) 'w_face%val', k, w_face%val
    1108            0 :             write(*,2) 'Lc_div_w_face', k, Lc_div_w_face%val
    1109            0 :             write(*,2) 'PII_face%val', k, PII_face%val
    1110            0 :             write(*,2) 'T_rho_face%val', k, T_rho_face%val
    1111              :             !write(*,2) '', k,
    1112              :             !write(*,2) '', k,
    1113            0 :             call mesa_error(__FILE__,__LINE__,'compute_Lc_terms')
    1114              :          end if
    1115            0 :       end function compute_Lc_terms
    1116              : 
    1117              : 
    1118            0 :       function compute_Lt(s, k, ierr) result(Lt)  ! erg s^-1
    1119              :          type (star_info), pointer :: s
    1120              :          integer, intent(in) :: k
    1121              :          type(auto_diff_real_star_order1) :: Lt
    1122              :          integer, intent(out) :: ierr
    1123              :          type(auto_diff_real_star_order1) :: r_00, area2, d_m1, d_00, &
    1124              :             rho2_face, Hp_face, w_m1, w_00, w_face, etrb_m1, etrb_00
    1125            0 :          real(dp) :: alpha_alpha_t, alfa, beta
    1126              :          include 'formats'
    1127            0 :          ierr = 0
    1128            0 :          if (k > s% nz) then
    1129            0 :             Lt = 0d0
    1130            0 :             return
    1131              :          end if
    1132            0 :          alpha_alpha_t = s% mixing_length_alpha*s% RSP2_alfat
    1133              :          if (alpha_alpha_t == 0d0 .or. &
    1134            0 :              k <= s% RSP2_num_outermost_cells_forced_nonturbulent .or. &
    1135              :              k > s% nz - int(s% nz/s% RSP2_nz_div_IBOTOM)) then
    1136            0 :             Lt = 0d0
    1137            0 :             s% Lt(k) = 0d0
    1138            0 :             return
    1139              :          end if
    1140            0 :          r_00 = wrap_r_00(s,k)
    1141            0 :          area2 = pow2(4d0*pi*pow2(r_00))
    1142            0 :          d_m1 = wrap_d_m1(s,k)
    1143            0 :          d_00 = wrap_d_00(s,k)
    1144            0 :          call get_RSP2_alfa_beta_face_weights(s, k, alfa, beta)
    1145            0 :          rho2_face = alfa*pow2(d_00) + beta*pow2(d_m1)
    1146            0 :          w_m1 = wrap_w_m1(s,k)
    1147            0 :          w_00 = wrap_w_00(s,k)
    1148            0 :          w_face = alfa*w_00 + beta*w_m1
    1149            0 :          etrb_m1 = wrap_etrb_m1(s,k)
    1150            0 :          etrb_00 = wrap_etrb_00(s,k)
    1151            0 :          Hp_face = wrap_Hp_00(s,k)
    1152              :          ! Ft = - alpha_t * rho_face * alpha * Hp_face * w_face * detrb/dr (thesis eqn 2.44)
    1153              :          ! replace dr by dm_bar/(area*rho_face)
    1154              :          ! Ft = - alpha_alpha_t * rho_face * Hp_face * w_face * (area*rho_face) * detrb/dm_bar
    1155              :          ! Lt = area * Ft
    1156              :          ! Lt = -alpha_alpha_t * (area*rho_face)**2 * Hp_face * w_face * (etrb(k-1) - etrb(k))/dm_bar
    1157            0 :          Lt = - alpha_alpha_t * area2 * rho2_face * Hp_face * w_face * (etrb_m1 - etrb_00) / s% dm_bar(k)
    1158              :          ! units = (cm^4) (g^2 cm^-6) (cm) (cm s^-1) (ergs g^-1) g^-1 = erg s^-1
    1159            0 :          s% Lt(k) = Lt%val
    1160            0 :       end function compute_Lt
    1161              : 
    1162              : 
    1163            0 :       subroutine set_etrb_start_vars(s, ierr)
    1164              :          type (star_info), pointer :: s
    1165              :          integer, intent(out) :: ierr
    1166              :          integer :: k
    1167              :          type(auto_diff_real_star_order1) :: Y_face, Lt
    1168              :          include 'formats'
    1169            0 :          ierr = 0
    1170            0 :          do k=1,s%nz
    1171            0 :             Y_face = compute_Y_face(s, k, ierr)
    1172            0 :             if (ierr /= 0) return
    1173            0 :             s% Y_face_start(k) = Y_face%val
    1174            0 :             Lt = compute_Lt(s, k, ierr)
    1175            0 :             if (ierr /= 0) return
    1176            0 :             s% Lt_start(k) = Lt%val
    1177            0 :             s% w_start(k) = s% w(k)
    1178            0 :             s% Hp_face_start(k) = s% Hp_face(k)
    1179              :          end do
    1180              :       end subroutine set_etrb_start_vars
    1181              : 
    1182              : 
    1183            0 :       subroutine RSP2_adjust_vars_before_call_solver(s, ierr)  ! replaces check_omega in RSP
    1184              :          ! JAK OKRESLIC OMEGA DLA PIERWSZEJ ITERACJI
    1185              :          use micro, only: do_eos_for_cell
    1186              :          type (star_info), pointer :: s
    1187              :          integer, intent(out) :: ierr
    1188            0 :          real(dp) :: PII_div_Hp, QQ, SOURCE, Hp_cell, DAMP, POM, POM2, DAMPR, del, soln
    1189              :          !type(auto_diff_real_star_order1) :: x
    1190              :          integer :: k
    1191              :          include 'formats'
    1192            0 :          ierr = 0
    1193            0 :          if (s% mixing_length_alpha == 0d0) return
    1194              : 
    1195            0 :          !$OMP PARALLEL DO PRIVATE(k,PII_div_Hp,QQ,SOURCE,Hp_cell,DAMP,POM,POM2,DAMPR,del,soln) SCHEDULE(dynamic,2)
    1196              :          do k=s% RSP2_num_outermost_cells_forced_nonturbulent+1, &
    1197              :                s% nz - max(1,int(s% nz/s% RSP_nz_div_IBOTOM))
    1198              : 
    1199              :             if (s% w(k) > s% RSP2_w_min_for_damping) cycle
    1200              : 
    1201              :             PII_div_Hp = 0.5d0*(s% PII(k)/s% Hp_face(k) + s% PII(k+1)/s% Hp_face(k+1))
    1202              :             QQ = s% chiT(k)/(s% rho(k)*s% T(k)*s% chiRho(k))
    1203              :             SOURCE = PII_div_Hp*s% T(k)*s% Peos(k)*QQ/s% Cp(k)
    1204              : 
    1205              :             Hp_cell = 0.5d0*(s% Hp_face(k) + s% Hp_face(k+1))
    1206              :             DAMP = (s% RSP2_alfad*x_CEDE/s% mixing_length_alpha)/Hp_cell
    1207              : 
    1208              :             POM = 4d0*boltz_sigma*pow2(s% RSP2_alfar*x_GAMMAR/s% mixing_length_alpha)
    1209              :             POM2 = pow3(s% T(k))/(pow2(s% rho(k))*s% Cp(k)*s% opacity(k))
    1210              :             DAMPR = POM*POM2/pow2(Hp_cell)
    1211              : 
    1212              :             del = pow2(DAMPR) + 4d0*DAMP*SOURCE
    1213              : 
    1214              :             if (k==-35) then
    1215              :                write(*,2) 'del', k, del
    1216              :                write(*,2) 'DAMPR', k, DAMPR
    1217              :                write(*,2) 'DAMP', k, DAMP
    1218              :                write(*,2) 'SOURCE', k, SOURCE
    1219              :                write(*,2) 'POM', k, PII_div_Hp
    1220              :                write(*,2) 'POM2', k, s% T(k)*s% Peos(k)*QQ/s% Cp(k)
    1221              :                write(*,2) 's% Hp_face(k)', k, s% Hp_face(k)
    1222              :                write(*,2) 's% Hp_face(k+1)', k+1, s% Hp_face(k+1)
    1223              :                write(*,2) 's% PII(k)', k, s% PII(k)
    1224              :                write(*,2) 's% PII(k+1)', k+1, s% PII(k+1)
    1225              :                write(*,2) 's% Y_face(k)', k, s% Y_face(k)
    1226              :                write(*,2) 's% Y_face(k+1)', k+1, s% Y_face(k+1)
    1227              :             end if
    1228              : 
    1229              :             if (del < 0d0) cycle
    1230              :             soln = (-DAMPR + sqrt(del))/(2d0*DAMP)
    1231              :             if (k==-35) write(*,2) 'soln', k, soln
    1232              :             if (soln > 0d0) then
    1233              :                ! i tried soln = sqrt(soln) here. helps solver convergence, but hurts the model results.
    1234              :                if (s% RSP2_report_adjust_w) &
    1235              :                   write(*,3) 'RSP2_adjust_vars_before_call_solver w', k, s% model_number, s% w(k), soln
    1236              :                s% w(k) = soln
    1237              :             end if
    1238              : 
    1239              :          end do
    1240              :          !$OMP END PARALLEL DO
    1241            0 :       end subroutine RSP2_adjust_vars_before_call_solver
    1242              : 
    1243              :       end module hydro_rsp2
        

Generated by: LCOV version 2.0-1