LCOV - code coverage report
Current view: top level - star/private - mesh_functions.f90 (source / functions) Coverage Total Hit
Test: coverage.info Lines: 60.6 % 160 97
Test Date: 2025-05-08 18:23:42 Functions: 80.0 % 5 4

            Line data    Source code
       1              : ! ***********************************************************************
       2              : !
       3              : !   Copyright (C) 2010-2019  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 mesh_functions
      21              : 
      22              :       use star_private_def
      23              :       use const_def, only: dp, ln10, msun, rsun, secyer
      24              :       use num_lib
      25              :       use utils_lib
      26              :       use chem_def
      27              : 
      28              :       implicit none
      29              : 
      30              :       private
      31              :       public :: num_mesh_functions, set_mesh_function_data, max_allowed_gvals
      32              : 
      33              :       integer, parameter :: max_allowed_gvals = 50
      34              : 
      35              :       contains
      36              : 
      37           30 :       integer function get_net_iso(s, species)
      38              :          use chem_lib, only: chem_get_iso_id
      39              :          type (star_info), pointer :: s
      40              :          character (len=*) :: species
      41              :          integer :: j
      42           30 :          get_net_iso = 0
      43           30 :          if (len_trim(species) == 0) return
      44           30 :          j = chem_get_iso_id(species)
      45           30 :          if (j <= 0) then
      46            0 :             write(*,*) 'unknown species name for mesh function: ' // trim(species)
      47            0 :             write(*,*) 'len_trim(species)', len_trim(species)
      48            0 :             return
      49              :          end if
      50           30 :          get_net_iso = s% net_iso(j)  ! 0 if species not in current net
      51           30 :       end function get_net_iso
      52              : 
      53              : 
      54          180 :       logical function do_mass_function(s,species,weight,j)
      55              :          type (star_info), pointer :: s
      56              :          character (len=iso_name_length) :: species
      57              :          real(dp), intent(in) :: weight
      58              :          integer, intent(out) :: j
      59          180 :          j = 0
      60           20 :          if (weight > 0) j = get_net_iso(s, species)
      61          200 :          do_mass_function = (j > 0)
      62           30 :       end function do_mass_function
      63              : 
      64              : 
      65           10 :       integer function num_mesh_functions(s)
      66              :          type (star_info), pointer :: s
      67              :          integer :: i, j, k
      68           10 :          i = 0
      69           10 :          if (s% use_other_mesh_functions) &
      70            0 :             call s% how_many_other_mesh_fcns(s% id, i)
      71           10 :          if (s% convective_bdy_weight > 0) i=i+1
      72           10 :          if (s% E_function_weight > 0) i=i+1
      73           10 :          if (s% P_function_weight > 0) i=i+1
      74           10 :          if (s% T_function1_weight > 0) i=i+1
      75           10 :          if (s% T_function2_weight > 0) i=i+1
      76           10 :          if (s% R_function_weight > 0) i=i+1
      77           10 :          if (s% R_function2_weight > 0) i=i+1
      78           10 :          if (s% R_function3_weight > 0) i=i+1
      79           10 :          if (s% M_function_weight > 0) i=i+1
      80           10 :          if (s% gradT_function_weight > 0) i=i+1
      81           10 :          if (s% log_tau_function_weight > 0) i=i+1
      82           10 :          if (s% log_kap_function_weight > 0) i=i+1
      83           10 :          if (s% gam_function_weight > 0) i=i+1
      84           10 :          if (s% omega_function_weight > 0 .and. s% rotation_flag) i=i+1
      85          100 :          do k=1,num_xa_function
      86          110 :             if (do_mass_function( &
      87              :                   s, s% xa_function_species(k), s% xa_function_weight(k), j)) &
      88           20 :                i=i+1
      89              :          end do
      90           10 :          num_mesh_functions = i
      91           10 :       end function num_mesh_functions
      92              : 
      93              : 
      94           10 :       subroutine set_mesh_function_data( &
      95              :             s, nfcns, names, gval_is_xa_function, gval_is_logT_function, vals1, ierr)
      96              :          type (star_info), pointer :: s
      97              :          integer, intent(in) :: nfcns
      98              :          character (len=32), intent(out) :: names(max_allowed_gvals)
      99              :          logical, intent(out), dimension(max_allowed_gvals) :: &
     100              :             gval_is_xa_function, gval_is_logT_function
     101              :          real(dp), pointer :: vals1(:)  ! =(nz, nfcns)
     102              :          integer, intent(out) :: ierr
     103              : 
     104              :          integer :: i, nz, j, k, i_other
     105              :          logical, parameter :: dbg = .false.
     106              :          real(dp), dimension(:,:), pointer :: vals
     107              : 
     108           10 :          ierr = 0
     109           10 :          nz = s% nz
     110              : 
     111           10 :          vals(1:nz,1:nfcns) => vals1(1:nz*nfcns)
     112           10 :          gval_is_xa_function = .false.
     113           10 :          gval_is_logT_function = .false.
     114              : 
     115           10 :          i_other = 0
     116           10 :          if (s% use_other_mesh_functions) then
     117            0 :             call s% how_many_other_mesh_fcns(s% id, i_other)
     118            0 :             if (i_other > 0) then
     119            0 :                if (i_other > nfcns) then
     120            0 :                   ierr = -1
     121            0 :                   return
     122              :                end if
     123              :                call s% other_mesh_fcn_data( &
     124            0 :                   s% id, i_other, names, gval_is_xa_function, vals1, ierr)
     125            0 :                if (ierr /= 0) return
     126              :             end if
     127              :          end if
     128              : 
     129           10 :          i = i_other
     130           10 :          if (s% E_function_weight > 0) then
     131            0 :             i = i+1; names(i) = 'E_function'
     132              :          end if
     133           10 :          if (s% P_function_weight > 0) then
     134           10 :             i = i+1; names(i) = 'P_function'
     135              :          end if
     136           10 :          if (s% T_function1_weight > 0) then
     137           10 :             i = i+1; names(i) = 'T_function1'
     138           10 :             gval_is_logT_function(i) = .true.
     139              :          end if
     140           10 :          if (s% T_function2_weight > 0) then
     141            0 :             i = i+1; names(i) = 'T_function2'
     142            0 :             gval_is_logT_function(i) = .true.
     143              :          end if
     144           10 :          if (s% R_function_weight > 0) then
     145            0 :             i = i+1; names(i) = 'R_function'
     146              :          end if
     147           10 :          if (s% R_function2_weight > 0) then
     148            0 :             i = i+1; names(i) = 'R_function2'
     149              :          end if
     150           10 :          if (s% R_function3_weight > 0) then
     151            0 :             i = i+1; names(i) = 'R_function3'
     152              :          end if
     153           10 :          if (s% M_function_weight > 0) then
     154            0 :             i = i+1; names(i) = 'M_function'
     155              :          end if
     156           10 :          if (s% gradT_function_weight > 0) then
     157            0 :             i = i+1; names(i) = 'gradT_function'
     158              :          end if
     159           10 :          if (s% log_tau_function_weight > 0) then
     160            0 :             i = i+1; names(i) = 'log_tau_function'
     161              :          end if
     162           10 :          if (s% log_kap_function_weight > 0) then
     163            0 :             i = i+1; names(i) = 'log_kap_function'
     164              :          end if
     165           10 :          if (s% gam_function_weight > 0) then
     166            0 :             i = i+1; names(i) = 'gam_function'
     167              :          end if
     168           10 :          if (s% omega_function_weight > 0 .and. s% rotation_flag) then
     169            0 :             i = i+1; names(i) = 'omega_function'
     170              :          end if
     171           10 :          if (s% convective_bdy_weight > 0) then
     172            0 :             i = i+1; names(i) = 'convective_bdy'
     173              :          end if
     174          100 :          do k=1,num_xa_function
     175          120 :             if (do_mass_function(s, s% xa_function_species(k), s% xa_function_weight(k), j)) then
     176           10 :                i = i+1; names(i) = trim(s% xa_function_species(k))
     177           10 :                gval_is_xa_function(i) = .true.
     178              :                !write(names(i),'(a,i1)') 'xa_function_', k
     179              :             end if
     180              :          end do
     181           10 :          if (i /= nfcns) then
     182            0 :             write(*,*) 'error in set_mesh_function_names: incorrect nfcns'
     183            0 :             ierr = -1
     184              :          end if
     185              : 
     186           40 :          do i=i_other+1,nfcns
     187              : 
     188           30 :             if (ierr /= 0) cycle
     189              :             if (dbg) write(*,*) trim(names(i))
     190              : 
     191           40 :             if (names(i) == 'E_function') then
     192            0 :                do k=1,nz
     193            0 :                   vals(k,i) = s% E_function_weight * max(s% E_function_param, s% lnE(k)/ln10)
     194              :                end do
     195              : 
     196           30 :             else if (names(i) == 'P_function') then
     197        12105 :                do k=1,nz
     198        12105 :                   vals(k,i) = s% P_function_weight * s% lnPeos(k)/ln10
     199              :                end do
     200              : 
     201           20 :             else if (names(i) == 'T_function1') then
     202        12105 :                do k=1,nz
     203        12105 :                   vals(k,i) = s% T_function1_weight*s% lnT(k)/ln10
     204              :                end do
     205              : 
     206           10 :             else if (names(i) == 'T_function2') then
     207            0 :                do k=1,nz
     208              :                   vals(k,i) = &
     209            0 :                      s% T_function2_weight*log10(s% T(k) / (s% T(k) + s% T_function2_param))
     210              :                end do
     211              : 
     212           10 :             else if (names(i) == 'R_function') then
     213            0 :                do k=1,nz
     214              :                   vals(k,i) = &
     215            0 :                      s% R_function_weight*log10(1 + (s% r(k)/Rsun)/s% R_function_param)
     216              :                end do
     217              : 
     218           10 :             else if (names(i) == 'R_function2') then
     219            0 :                do k=1,nz
     220              :                   vals(k,i) = &
     221              :                      s% R_function2_weight * &
     222            0 :                      min(s% R_function2_param1, max(s% R_function2_param2,s% r(k)/s% r(1)))
     223              :                end do
     224              : 
     225           10 :             else if (names(i) == 'R_function3') then
     226            0 :                do k=1,nz
     227            0 :                   vals(k,i) = s% R_function3_weight*s% r(k)/s% r(1)
     228              :                end do
     229              : 
     230           10 :             else if (names(i) == 'M_function') then
     231            0 :                do k=1,nz
     232              :                   vals(k,i) = &
     233            0 :                   s% M_function_weight*log10(1 + (s% xmstar*s% q(k)/Msun)/s% M_function_param)
     234              :                end do
     235              : 
     236           10 :             else if (names(i) == 'gradT_function') then
     237            0 :                do k=1,nz
     238            0 :                   vals(k,i) = s% gradT_function_weight*s% gradT(k)
     239              :                end do
     240              : 
     241           10 :             else if (names(i) == 'log_tau_function') then
     242            0 :                do k=1,nz
     243            0 :                   vals(k,i) = s% log_tau_function_weight*log10(s% tau(k))
     244              :                end do
     245              : 
     246           10 :             else if (names(i) == 'log_kap_function') then
     247            0 :                do k=1,nz
     248            0 :                   vals(k,i) = s% log_kap_function_weight*log10(s% opacity(k))
     249              :                end do
     250              : 
     251           10 :             else if (names(i) == 'gam_function') then
     252            0 :                do k=1,nz
     253              :                   vals(k,i) = s% gam_function_weight* &
     254            0 :                      tanh((s% gam(k) - s% gam_function_param1)/s% gam_function_param2)
     255              :                end do
     256              : 
     257           10 :             else if (names(i) == 'omega_function') then
     258            0 :                do k=1,nz
     259            0 :                   vals(k,i) = s% omega_function_weight*log10(max(1d-99,abs(s% omega(k))))
     260              :                end do
     261              : 
     262           10 :             else if (names(i) == 'convective_bdy') then
     263            0 :                call do_conv_bdy(i)
     264              : 
     265              :             else
     266          100 :                do k=1,num_xa_function
     267          100 :                   call do1_xa_function(k,i)
     268              :                end do
     269              : 
     270              :             end if
     271              : 
     272              :          end do
     273              : 
     274              :          contains
     275              : 
     276              : 
     277            0 :          subroutine do_conv_bdy(i)
     278              :             integer, intent(in) :: i
     279              :             integer :: k, j
     280              : 
     281            0 :             vals(1:nz,i) = 0
     282              : 
     283            0 :             if (s% dt < s% convective_bdy_min_dt_yrs*secyer) return
     284              : 
     285              :             !do k=1,nz
     286              :             !   if (s% dq(k) < s% convective_bdy_dq_limit) cycle
     287              :             !   if (s% cz_bdy_dq(k) /= 0) vals(k,i) = s% convective_bdy_weight
     288              :             !end do
     289              : 
     290            0 :             do j = 1, s% num_conv_boundaries
     291            0 :                k = s% conv_bdy_loc(j)
     292            0 :                if (s% dq(k) < s% convective_bdy_dq_limit) cycle
     293            0 :                vals(k,i) = s% convective_bdy_weight
     294            0 :                if (k < nz .and. s% top_conv_bdy(i)) then
     295            0 :                   vals(k+1,i) = s% convective_bdy_weight
     296            0 :                else if (k > 1 .and. .not. s% top_conv_bdy(i)) then
     297            0 :                   vals(k-1,i) = s% convective_bdy_weight
     298              :                end if
     299              :             end do
     300              : 
     301            0 :             do k=2,nz
     302            0 :                vals(k,i) = vals(k,i) + vals(k-1,i)
     303              :             end do
     304              : 
     305              :          end subroutine do_conv_bdy
     306              : 
     307           90 :          subroutine do1_xa_function(k,i)
     308              :             integer, intent(in) :: k,i
     309           90 :             real(dp) :: weight, param
     310              :             integer :: j, m
     311           90 :             if (len_trim(s% xa_function_species(k))==0) return
     312           10 :             if (trim(names(i)) /= trim(s% xa_function_species(k))) return
     313           10 :             j = get_net_iso(s, s% xa_function_species(k))
     314           10 :             if (j <= 0) then
     315            0 :                ierr = -1
     316              :             else
     317           10 :                weight = s% xa_function_weight(k)
     318           10 :                param = s% xa_function_param(k)
     319        12105 :                do m=1,s% nz
     320        12105 :                   vals(m,i) = weight*log10(s% xa(j,m) + param)
     321              :                end do
     322              :             end if
     323              :          end subroutine do1_xa_function
     324              : 
     325              :       end subroutine set_mesh_function_data
     326              : 
     327              :       end module mesh_functions
        

Generated by: LCOV version 2.0-1