Imposes the diapycnal mass fluxes and the accompanying diapycnal advection of momentum and tracers using the original MOM6 algorithms.
1855 type(ocean_grid_type),
intent(inout) :: G
1856 type(verticalGrid_type),
intent(in) :: GV
1857 type(unit_scale_type),
intent(in) :: US
1858 real,
dimension(SZIB_(G),SZJ_(G),SZK_(G)),
intent(inout) :: u
1859 real,
dimension(SZI_(G),SZJB_(G),SZK_(G)),
intent(inout) :: v
1860 real,
dimension(SZI_(G),SZJ_(G),SZK_(G)),
intent(inout) :: h
1861 type(thermo_var_ptrs),
intent(inout) :: tv
1863 real,
dimension(:,:),
pointer :: Hml
1864 type(forcing),
intent(inout) :: fluxes
1866 type(vertvisc_type),
intent(inout) :: visc
1867 type(accel_diag_ptrs),
intent(inout) :: ADp
1870 type(cont_diag_ptrs),
intent(inout) :: CDp
1871 real,
intent(in) :: dt
1872 type(time_type),
intent(in) :: Time_end
1873 type(diabatic_CS),
pointer :: CS
1874 type(Wave_parameters_CS),
optional,
pointer :: Waves
1876 real,
dimension(SZI_(G),SZJ_(G),SZK_(G)) :: &
1891 real,
dimension(SZI_(G),SZJ_(G)) :: &
1894 real,
dimension(SZI_(G),SZJ_(G),G%ke) :: h_diag
1895 real,
dimension(SZI_(G),SZJ_(G),G%ke) :: temp_diag
1896 real,
dimension(SZI_(G),SZJ_(G),G%ke) :: saln_diag
1897 real,
dimension(SZI_(G),SZJ_(G)) :: tendency_2d
1901 real,
dimension(SZI_(G),SZJ_(G),SZK_(G)),
target :: &
1907 real,
dimension(SZI_(G),SZJ_(G),SZK_(G)+1) :: &
1921 real,
allocatable,
dimension(:,:) :: &
1922 hf_dudt_dia_2d, hf_dvdt_dia_2d
1925 real,
pointer,
dimension(:,:,:) :: &
1931 integer :: kb(SZI_(G),SZJ_(G))
1934 real :: p_ref_cv(SZI_(G))
1937 logical :: in_boundary(SZI_(G))
1957 real :: htot(SZIB_(G))
1958 real :: b1(SZIB_(G)), d1(SZIB_(G))
1959 real :: c1(SZIB_(G),SZK_(G))
1966 logical :: showCallTree
1967 integer,
dimension(2) :: EOSdom
1968 integer :: i, j, k, is, ie, js, je, Isq, Ieq, Jsq, Jeq, nz, nkmb, m, halo
1970 is = g%isc ; ie = g%iec ; js = g%jsc ; je = g%jec ; nz = g%ke
1971 isq = g%IscB ; ieq = g%IecB ; jsq = g%JscB ; jeq = g%JecB
1972 nkmb = gv%nk_rho_varies
1973 h_neglect = gv%H_subroundoff ; h_neglect2 = h_neglect*h_neglect
1974 kd_heat(:,:,:) = 0.0 ; kd_salt(:,:,:) = 0.0
1977 showcalltree = calltree_showquery()
1978 if (showcalltree)
call calltree_enter(
"layered_diabatic(), MOM_diabatic_driver.F90")
1981 eaml => eatr ; ebml => ebtr
1984 call enable_averages(dt, time_end, cs%diag)
1986 if ((cs%ML_mix_first > 0.0) .or. cs%use_geothermal)
then 1987 halo = cs%halo_TS_diff
1989 do k=1,nz ;
do j=js-halo,je+halo ;
do i=is-halo,ie+halo
1990 h_orig(i,j,k) = h(i,j,k) ; eaml(i,j,k) = 0.0 ; ebml(i,j,k) = 0.0
1991 enddo ;
enddo ;
enddo 1994 if (cs%use_geothermal)
then 1995 call cpu_clock_begin(id_clock_geothermal)
1996 call geothermal_entraining(h, tv, dt, eaml, ebml, g, gv, us, cs%geothermal_CSp, halo=cs%halo_TS_diff)
1997 call cpu_clock_end(id_clock_geothermal)
1998 if (showcalltree)
call calltree_waypoint(
"geothermal (diabatic)")
1999 if (cs%debugConservation)
call mom_state_stats(
'geothermal', u, v, h, tv%T, tv%S, g, gv, us)
2004 call diag_update_remap_grids(cs%diag)
2009 if (
associated(cs%optics)) &
2010 call set_pen_shortwave(cs%optics, fluxes, g, gv, us, cs%diabatic_aux_CSp, cs%opacity_CSp, cs%tracer_flow_CSp)
2012 if (cs%bulkmixedlayer)
then 2013 if (cs%debug)
call mom_forcing_chksum(
"Before mixedlayer", fluxes, g, us, haloshift=0)
2015 if (cs%ML_mix_first > 0.0)
then 2023 call find_uv_at_h(u, v, h, u_h, v_h, g, gv, us)
2025 call cpu_clock_begin(id_clock_mixedlayer)
2026 if (cs%ML_mix_first < 1.0)
then 2028 call bulkmixedlayer(h, u_h, v_h, tv, fluxes, dt*cs%ML_mix_first, &
2029 eaml,ebml, g, gv, us, cs%bulkmixedlayer_CSp, cs%optics, &
2030 hml, cs%aggregate_FW_forcing, dt, last_call=.false.)
2032 call bulkmixedlayer(h, u_h, v_h, tv, fluxes, dt, eaml, ebml, &
2033 g, gv, us, cs%bulkmixedlayer_CSp, cs%optics, &
2034 hml, cs%aggregate_FW_forcing, dt, last_call=.true.)
2043 if (
associated(tv%S) .and.
associated(tv%salt_deficit)) &
2044 call adjust_salt(h, tv, g, gv, cs%diabatic_aux_CSp)
2045 call cpu_clock_end(id_clock_mixedlayer)
2047 call mom_state_chksum(
"After mixedlayer ", u, v, h, g, gv, us, haloshift=0)
2048 call mom_forcing_chksum(
"After mixedlayer", fluxes, g, us, haloshift=0)
2050 if (showcalltree)
call calltree_waypoint(
"done with 1st bulkmixedlayer (diabatic)")
2051 if (cs%debugConservation)
call mom_state_stats(
'1st bulkmixedlayer', u, v, h, tv%T, tv%S, g, gv, us)
2056 call mom_state_chksum(
"before find_uv_at_h", u, v, h, g, gv, us, haloshift=0)
2057 if (cs%use_kappa_shear .or. cs%use_CVMix_shear)
then 2058 if ((cs%ML_mix_first > 0.0) .or. cs%use_geothermal)
then 2059 call find_uv_at_h(u, v, h_orig, u_h, v_h, g, gv, us, eaml, ebml)
2061 call hchksum(eaml,
"after find_uv_at_h eaml", g%HI, scale=gv%H_to_m)
2062 call hchksum(ebml,
"after find_uv_at_h ebml", g%HI, scale=gv%H_to_m)
2065 call find_uv_at_h(u, v, h, u_h, v_h, g, gv, us)
2067 if (showcalltree)
call calltree_waypoint(
"done with find_uv_at_h (diabatic)")
2070 call cpu_clock_begin(id_clock_set_diffusivity)
2073 if ((cs%halo_TS_diff > 0) .and. (cs%ML_mix_first > 0.0))
then 2074 if (
associated(tv%T))
call pass_var(tv%T, g%Domain, halo=cs%halo_TS_diff, complete=.false.)
2075 if (
associated(tv%T))
call pass_var(tv%S, g%Domain, halo=cs%halo_TS_diff, complete=.false.)
2076 call pass_var(h, g%domain, halo=cs%halo_TS_diff, complete=.true.)
2079 call mom_state_chksum(
"before set_diffusivity", u, v, h, g, gv, us, haloshift=cs%halo_TS_diff)
2080 if (cs%double_diffuse)
then 2081 call set_diffusivity(u, v, h, u_h, v_h, tv, fluxes, cs%optics, visc, dt, g, gv, us, cs%set_diff_CSp, &
2082 kd_lay=kd_lay, kd_int=kd_int, kd_extra_t=kd_extra_t, kd_extra_s=kd_extra_s)
2084 call set_diffusivity(u, v, h, u_h, v_h, tv, fluxes, cs%optics, visc, dt, g, gv, us, &
2085 cs%set_diff_CSp, kd_lay=kd_lay, kd_int=kd_int)
2087 call cpu_clock_end(id_clock_set_diffusivity)
2088 if (showcalltree)
call calltree_waypoint(
"done with set_diffusivity (diabatic)")
2091 call mom_state_chksum(
"after set_diffusivity ", u, v, h, g, gv, us, haloshift=0)
2092 call mom_forcing_chksum(
"after set_diffusivity ", fluxes, g, us, haloshift=0)
2093 call mom_thermovar_chksum(
"after set_diffusivity ", tv, g)
2094 call hchksum(kd_lay,
"after set_diffusivity Kd_lay", g%HI, haloshift=0, scale=us%Z2_T_to_m2_s)
2095 call hchksum(kd_int,
"after set_diffusivity Kd_Int", g%HI, haloshift=0, scale=us%Z2_T_to_m2_s)
2100 call cpu_clock_begin(id_clock_kpp)
2106 call calculatebuoyancyflux2d(g, gv, us, fluxes, cs%optics, h, tv%T, tv%S, tv, &
2107 cs%KPP_buoy_flux, cs%KPP_temp_flux, cs%KPP_salt_flux)
2112 if (cs%double_diffuse)
then 2115 do k=1,nz+1 ;
do j=js,je ;
do i=is,ie
2116 kd_salt(i,j,k) = kd_int(i,j,k) + kd_extra_s(i,j,k)
2117 kd_heat(i,j,k) = kd_int(i,j,k) + kd_extra_t(i,j,k)
2118 enddo ;
enddo ;
enddo 2121 do k=1,nz+1 ;
do j=js,je ;
do i=is,ie
2122 kd_salt(i,j,k) = kd_int(i,j,k)
2123 kd_heat(i,j,k) = kd_int(i,j,k)
2124 enddo ;
enddo ;
enddo 2127 call kpp_compute_bld(cs%KPP_CSp, g, gv, us, h, tv%T, tv%S, u, v, tv, &
2128 fluxes%ustar, cs%KPP_buoy_flux, waves=waves)
2130 call kpp_calculate(cs%KPP_CSp, g, gv, us, h, fluxes%ustar, cs%KPP_buoy_flux, kd_heat, &
2131 kd_salt, visc%Kv_shear, cs%KPP_NLTheat, cs%KPP_NLTscalar, waves=waves)
2133 if (
associated(hml))
then 2134 call kpp_get_bld(cs%KPP_CSp, hml(:,:), g, us)
2135 call pass_var(hml, g%domain, halo=1)
2137 if (
associated(visc%MLD)) visc%MLD(:,:) = hml(:,:)
2140 if (.not. cs%KPPisPassive)
then 2142 do k=1,nz+1 ;
do j=js,je ;
do i=is,ie
2143 kd_int(i,j,k) = min( kd_salt(i,j,k), kd_heat(i,j,k) )
2144 enddo ;
enddo ;
enddo 2145 if (cs%double_diffuse)
then 2147 do k=1,nz+1 ;
do j=js,je ;
do i=is,ie
2148 kd_extra_s(i,j,k) = (kd_salt(i,j,k) - kd_int(i,j,k))
2149 kd_extra_t(i,j,k) = (kd_heat(i,j,k) - kd_int(i,j,k))
2150 enddo ;
enddo ;
enddo 2154 call cpu_clock_end(id_clock_kpp)
2155 if (showcalltree)
call calltree_waypoint(
"done with KPP_calculate (diabatic)")
2157 call mom_state_chksum(
"after KPP", u, v, h, g, gv, us, haloshift=0)
2158 call mom_forcing_chksum(
"after KPP", fluxes, g, us, haloshift=0)
2159 call mom_thermovar_chksum(
"after KPP", tv, g)
2160 call hchksum(kd_lay,
"after KPP Kd_lay", g%HI, haloshift=0, scale=us%Z2_T_to_m2_s)
2161 call hchksum(kd_int,
"after KPP Kd_Int", g%HI, haloshift=0, scale=us%Z2_T_to_m2_s)
2167 if (cs%use_CVMix_conv)
then 2168 call calculate_cvmix_conv(h, tv, g, gv, us, cs%CVMix_conv_csp, hml, kd=kd_int, kv=visc%Kv_slow)
2172 call cpu_clock_begin(id_clock_kpp)
2174 call hchksum(cs%KPP_temp_flux,
"before KPP_applyNLT netHeat", g%HI, haloshift=0, scale=gv%H_to_m)
2175 call hchksum(cs%KPP_salt_flux,
"before KPP_applyNLT netSalt", g%HI, haloshift=0, scale=gv%H_to_m)
2176 call hchksum(cs%KPP_NLTheat,
"before KPP_applyNLT NLTheat", g%HI, haloshift=0)
2177 call hchksum(cs%KPP_NLTscalar,
"before KPP_applyNLT NLTscalar", g%HI, haloshift=0)
2181 call kpp_nonlocaltransport_temp(cs%KPP_CSp, g, gv, h, cs%KPP_NLTheat, cs%KPP_temp_flux, &
2182 us%T_to_s*dt, tv%T, us%Q_to_J_kg*tv%C_p)
2183 call kpp_nonlocaltransport_saln(cs%KPP_CSp, g, gv, h, cs%KPP_NLTscalar, cs%KPP_salt_flux, &
2185 call cpu_clock_end(id_clock_kpp)
2186 if (showcalltree)
call calltree_waypoint(
"done with KPP_applyNonLocalTransport (diabatic)")
2187 if (cs%debugConservation)
call mom_state_stats(
'KPP_applyNonLocalTransport', u, v, h, tv%T, tv%S, g, gv, us)
2190 call mom_state_chksum(
"after KPP_applyNLT ", u, v, h, g, gv, us, haloshift=0)
2191 call mom_forcing_chksum(
"after KPP_applyNLT ", fluxes, g, us, haloshift=0)
2192 call mom_thermovar_chksum(
"after KPP_applyNLT ", tv, g)
2198 if (cs%double_diffuse .and.
associated(tv%T))
then 2200 call cpu_clock_begin(id_clock_differential_diff)
2201 call differential_diffuse_t_s(h, tv%T, tv%S, kd_extra_t, kd_extra_s, dt, g, gv)
2202 call cpu_clock_end(id_clock_differential_diff)
2203 if (showcalltree)
call calltree_waypoint(
"done with differential_diffuse_T_S (diabatic)")
2204 if (cs%debugConservation)
call mom_state_stats(
'differential_diffuse_T_S', u, v, h, tv%T, tv%S, g, gv, us)
2208 if (.not. cs%useKPP)
then 2210 do k=2,nz ;
do j=js,je ;
do i=is,ie
2211 kd_heat(i,j,k) = kd_heat(i,j,k) + kd_extra_t(i,j,k)
2212 kd_salt(i,j,k) = kd_salt(i,j,k) + kd_extra_s(i,j,k)
2213 enddo ;
enddo ;
enddo 2220 call cpu_clock_begin(id_clock_entrain)
2223 call entrainment_diffusive(h, tv, fluxes, dt, g, gv, us, cs%entrain_diffusive_CSp, &
2224 ea, eb, kb, kd_lay=kd_lay, kd_int=kd_int)
2225 call cpu_clock_end(id_clock_entrain)
2226 if (showcalltree)
call calltree_waypoint(
"done with Entrainment_diffusive (diabatic)")
2229 call mom_forcing_chksum(
"after calc_entrain ", fluxes, g, us, haloshift=0)
2230 call mom_thermovar_chksum(
"after calc_entrain ", tv, g)
2231 call mom_state_chksum(
"after calc_entrain ", u, v, h, g, gv, us, haloshift=0)
2232 call hchksum(ea,
"after calc_entrain ea", g%HI, haloshift=0, scale=gv%H_to_m)
2233 call hchksum(eb,
"after calc_entrain eb", g%HI, haloshift=0, scale=gv%H_to_m)
2237 if (cs%boundary_forcing_tendency_diag)
then 2238 do k=1,nz ;
do j=js,je ;
do i=is,ie
2239 h_diag(i,j,k) = h(i,j,k)
2240 temp_diag(i,j,k) = tv%T(i,j,k)
2241 saln_diag(i,j,k) = tv%S(i,j,k)
2242 enddo ;
enddo ;
enddo 2256 hold(i,j,1) = h(i,j,1)
2257 h(i,j,1) = h(i,j,1) + (eb(i,j,1) - ea(i,j,2))
2258 hold(i,j,nz) = h(i,j,nz)
2259 h(i,j,nz) = h(i,j,nz) + (ea(i,j,nz) - eb(i,j,nz-1))
2260 if (h(i,j,1) <= 0.0)
then 2261 h(i,j,1) = gv%Angstrom_H
2263 if (h(i,j,nz) <= 0.0)
then 2264 h(i,j,nz) = gv%Angstrom_H
2267 do k=2,nz-1 ;
do i=is,ie
2268 hold(i,j,k) = h(i,j,k)
2269 h(i,j,k) = h(i,j,k) + ((ea(i,j,k) - eb(i,j,k-1)) + &
2270 (eb(i,j,k) - ea(i,j,k+1)))
2271 if (h(i,j,k) <= 0.0)
then 2272 h(i,j,k) = gv%Angstrom_H
2277 call diag_update_remap_grids(cs%diag)
2280 call mom_state_chksum(
"after negative check ", u, v, h, g, gv, us, haloshift=0)
2281 call mom_forcing_chksum(
"after negative check ", fluxes, g, us, haloshift=0)
2282 call mom_thermovar_chksum(
"after negative check ", tv, g)
2284 if (showcalltree)
call calltree_waypoint(
"done with h=ea-eb (diabatic)")
2285 if (cs%debugConservation)
call mom_state_stats(
'h=ea-eb', u, v, h, tv%T, tv%S, g, gv, us)
2291 if (cs%bulkmixedlayer)
then 2293 if (
associated(tv%T))
then 2294 call cpu_clock_begin(id_clock_tridiag)
2299 if (cs%massless_match_targets)
then 2303 h_tr = hold(i,j,1) + h_neglect
2304 b1(i) = 1.0 / (h_tr + eb(i,j,1))
2305 d1(i) = h_tr * b1(i)
2306 tv%T(i,j,1) = b1(i) * (h_tr*tv%T(i,j,1))
2307 tv%S(i,j,1) = b1(i) * (h_tr*tv%S(i,j,1))
2309 do k=2,nkmb ;
do i=is,ie
2310 c1(i,k) = eb(i,j,k-1) * b1(i)
2311 h_tr = hold(i,j,k) + h_neglect
2312 b_denom_1 = h_tr + d1(i)*ea(i,j,k)
2313 b1(i) = 1.0 / (b_denom_1 + eb(i,j,k))
2314 if (k<nkmb) d1(i) = b_denom_1 * b1(i)
2315 tv%T(i,j,k) = b1(i) * (h_tr*tv%T(i,j,k) + ea(i,j,k)*tv%T(i,j,k-1))
2316 tv%S(i,j,k) = b1(i) * (h_tr*tv%S(i,j,k) + ea(i,j,k)*tv%S(i,j,k-1))
2319 do k=nkmb+1,nz ;
do i=is,ie
2320 if (k == kb(i,j))
then 2321 c1(i,k) = eb(i,j,k-1) * b1(i)
2322 d1(i) = (((eb(i,j,nkmb)-eb(i,j,k-1)) + hold(i,j,nkmb) + h_neglect) + &
2323 d1(i)*ea(i,j,nkmb)) * b1(i)
2324 h_tr = hold(i,j,k) + h_neglect
2325 b_denom_1 = h_tr + d1(i)*ea(i,j,k)
2326 b1(i) = 1.0 / (b_denom_1 + eb(i,j,k))
2327 d1(i) = b_denom_1 * b1(i)
2328 tv%T(i,j,k) = b1(i) * (h_tr*tv%T(i,j,k) + ea(i,j,k)*tv%T(i,j,nkmb))
2329 tv%S(i,j,k) = b1(i) * (h_tr*tv%S(i,j,k) + ea(i,j,k)*tv%S(i,j,nkmb))
2330 elseif (k > kb(i,j))
then 2331 c1(i,k) = eb(i,j,k-1) * b1(i)
2332 h_tr = hold(i,j,k) + h_neglect
2333 b_denom_1 = h_tr + d1(i)*ea(i,j,k)
2334 b1(i) = 1.0 / (b_denom_1 + eb(i,j,k))
2335 d1(i) = b_denom_1 * b1(i)
2336 tv%T(i,j,k) = b1(i) * (h_tr*tv%T(i,j,k) + ea(i,j,k)*tv%T(i,j,k-1))
2337 tv%S(i,j,k) = b1(i) * (h_tr*tv%S(i,j,k) + ea(i,j,k)*tv%S(i,j,k-1))
2338 elseif (eb(i,j,k) < eb(i,j,k-1))
then 2343 tv%T(i,j,nkmb) = tv%T(i,j,nkmb) + b1(i) * (eb(i,j,k-1) - eb(i,j,k)) * tv%T(i,j,k)
2344 tv%S(i,j,nkmb) = tv%S(i,j,nkmb) + b1(i) * (eb(i,j,k-1) - eb(i,j,k)) * tv%S(i,j,k)
2348 do k=nz-1,nkmb,-1 ;
do i=is,ie
2349 if (k >= kb(i,j))
then 2350 tv%T(i,j,k) = tv%T(i,j,k) + c1(i,k+1)*tv%T(i,j,k+1)
2351 tv%S(i,j,k) = tv%S(i,j,k) + c1(i,k+1)*tv%S(i,j,k+1)
2354 do i=is,ie ;
if (kb(i,j) <= nz)
then 2355 tv%T(i,j,nkmb) = tv%T(i,j,nkmb) + c1(i,kb(i,j))*tv%T(i,j,kb(i,j))
2356 tv%S(i,j,nkmb) = tv%S(i,j,nkmb) + c1(i,kb(i,j))*tv%S(i,j,kb(i,j))
2358 do k=nkmb-1,1,-1 ;
do i=is,ie
2359 tv%T(i,j,k) = tv%T(i,j,k) + c1(i,k+1)*tv%T(i,j,k+1)
2360 tv%S(i,j,k) = tv%S(i,j,k) + c1(i,k+1)*tv%S(i,j,k+1)
2367 if (cs%tracer_tridiag)
then 2368 call tracer_vertdiff(hold, ea, eb, dt, tv%T, g, gv)
2369 call tracer_vertdiff(hold, ea, eb, dt, tv%S, g, gv)
2371 call tridiagts(g, gv, is, ie, js, je, hold, ea, eb, tv%T, tv%S)
2374 call cpu_clock_end(id_clock_tridiag)
2377 if (cs%debugConservation)
call mom_state_stats(
'BML tridiag', u, v, h, tv%T, tv%S, g, gv, us)
2379 if ((cs%ML_mix_first > 0.0) .or. cs%use_geothermal)
then 2383 do k=1,nz ;
do j=js,je ;
do i=is,ie
2384 hold(i,j,k) = h_orig(i,j,k)
2385 ea(i,j,k) = ea(i,j,k) + eaml(i,j,k)
2386 eb(i,j,k) = eb(i,j,k) + ebml(i,j,k)
2387 enddo ;
enddo ;
enddo 2389 call hchksum(ea,
"after ea = ea + eaml", g%HI, haloshift=0, scale=gv%H_to_m)
2390 call hchksum(eb,
"after eb = eb + ebml", g%HI, haloshift=0, scale=gv%H_to_m)
2394 if (cs%ML_mix_first < 1.0)
then 2403 call find_uv_at_h(u, v, hold, u_h, v_h, g, gv, us, ea, eb)
2404 if (cs%debug)
call mom_state_chksum(
"find_uv_at_h1 ", u, v, h, g, gv, us, haloshift=0)
2406 dt_mix = min(dt, dt*(1.0 - cs%ML_mix_first))
2407 call cpu_clock_begin(id_clock_mixedlayer)
2409 call bulkmixedlayer(h, u_h, v_h, tv, fluxes, dt_mix, ea, eb, &
2410 g, gv, us, cs%bulkmixedlayer_CSp, cs%optics, &
2411 hml, cs%aggregate_FW_forcing, dt, last_call=.true.)
2419 if (
associated(tv%S) .and.
associated(tv%salt_deficit)) &
2420 call adjust_salt(h, tv, g, gv, cs%diabatic_aux_CSp)
2422 call cpu_clock_end(id_clock_mixedlayer)
2423 if (showcalltree)
call calltree_waypoint(
"done with 2nd bulkmixedlayer (diabatic)")
2424 if (cs%debugConservation)
call mom_state_stats(
'2nd bulkmixedlayer', u, v, h, tv%T, tv%S, g, gv, us)
2430 if (
associated(tv%T))
then 2433 call hchksum(ea,
"before triDiagTS ea ", g%HI, haloshift=0, scale=gv%H_to_m)
2434 call hchksum(eb,
"before triDiagTS eb ", g%HI, haloshift=0, scale=gv%H_to_m)
2436 call cpu_clock_begin(id_clock_tridiag)
2444 if (
associated(tv%S) .and.
associated(tv%salt_deficit)) &
2445 call adjust_salt(h, tv, g, gv, cs%diabatic_aux_CSp)
2447 if (cs%diabatic_diff_tendency_diag)
then 2448 do k=1,nz ;
do j=js,je ;
do i=is,ie
2449 temp_diag(i,j,k) = tv%T(i,j,k)
2450 saln_diag(i,j,k) = tv%S(i,j,k)
2451 enddo ;
enddo ;
enddo 2455 if (cs%tracer_tridiag)
then 2456 call tracer_vertdiff(hold, ea, eb, dt, tv%T, g, gv)
2457 call tracer_vertdiff(hold, ea, eb, dt, tv%S, g, gv)
2459 call tridiagts(g, gv, is, ie, js, je, hold, ea, eb, tv%T, tv%S)
2465 if (cs%diabatic_diff_tendency_diag)
then 2466 call diagnose_diabatic_diff_tendency(tv, hold, temp_diag, saln_diag, dt, g, gv, us, cs)
2467 if (cs%id_diabatic_diff_h > 0)
call post_data(cs%id_diabatic_diff_h, hold, cs%diag, alt_h=hold)
2470 call cpu_clock_end(id_clock_tridiag)
2471 if (showcalltree)
call calltree_waypoint(
"done with triDiagTS (diabatic)")
2474 if (cs%debugConservation)
call mom_state_stats(
'triDiagTS', u, v, h, tv%T, tv%S, g, gv, us)
2479 call mom_state_chksum(
"after mixed layer ", u, v, h, g, gv, us, haloshift=0)
2480 call mom_thermovar_chksum(
"after mixed layer ", tv, g)
2481 call hchksum(ea,
"after mixed layer ea", g%HI, scale=gv%H_to_m)
2482 call hchksum(eb,
"after mixed layer eb", g%HI, scale=gv%H_to_m)
2485 call cpu_clock_begin(id_clock_remap)
2486 call regularize_layers(h, tv, dt, ea, eb, g, gv, us, cs%regularize_layers_CSp)
2487 call cpu_clock_end(id_clock_remap)
2488 if (showcalltree)
call calltree_waypoint(
"done with regularize_layers (diabatic)")
2489 if (cs%debugConservation)
call mom_state_stats(
'regularize_layers', u, v, h, tv%T, tv%S, g, gv, us)
2493 if (
associated(adp%du_dt_dia) .or.
associated(adp%dv_dt_dia)) &
2495 call pass_var(h, g%domain, to_west+to_south+omit_corners, halo=1)
2496 call diag_update_remap_grids(cs%diag)
2500 if ((cs%id_Tdif > 0) .or. (cs%id_Tadv > 0))
then 2501 do j=js,je ;
do i=is,ie
2502 tdif_flx(i,j,1) = 0.0 ; tdif_flx(i,j,nz+1) = 0.0
2503 tadv_flx(i,j,1) = 0.0 ; tadv_flx(i,j,nz+1) = 0.0
2506 do k=2,nz ;
do j=js,je ;
do i=is,ie
2507 tdif_flx(i,j,k) = (idt * 0.5*(ea(i,j,k) + eb(i,j,k-1))) * &
2508 (tv%T(i,j,k-1) - tv%T(i,j,k))
2509 tadv_flx(i,j,k) = (idt * (ea(i,j,k) - eb(i,j,k-1))) * &
2510 0.5*(tv%T(i,j,k-1) + tv%T(i,j,k))
2511 enddo ;
enddo ;
enddo 2513 if ((cs%id_Sdif > 0) .or. (cs%id_Sadv > 0))
then 2514 do j=js,je ;
do i=is,ie
2515 sdif_flx(i,j,1) = 0.0 ; sdif_flx(i,j,nz+1) = 0.0
2516 sadv_flx(i,j,1) = 0.0 ; sadv_flx(i,j,nz+1) = 0.0
2519 do k=2,nz ;
do j=js,je ;
do i=is,ie
2520 sdif_flx(i,j,k) = (idt * 0.5*(ea(i,j,k) + eb(i,j,k-1))) * &
2521 (tv%S(i,j,k-1) - tv%S(i,j,k))
2522 sadv_flx(i,j,k) = (idt * (ea(i,j,k) - eb(i,j,k-1))) * &
2523 0.5*(tv%S(i,j,k-1) + tv%S(i,j,k))
2524 enddo ;
enddo ;
enddo 2528 call cpu_clock_begin(id_clock_tracers)
2529 if (cs%mix_boundary_tracers)
then 2530 tr_ea_bbl = gv%Z_to_H * sqrt(dt*cs%Kd_BBL_tr)
2534 ebtr(i,j,nz) = eb(i,j,nz)
2536 in_boundary(i) = (g%mask2dT(i,j) > 0.0)
2538 do k=nz,2,-1 ;
do i=is,ie
2539 if (in_boundary(i))
then 2540 htot(i) = htot(i) + h(i,j,k)
2549 add_ent = ((dt * cs%Kd_min_tr) * gv%Z_to_H**2) * &
2550 ((h(i,j,k-1)+h(i,j,k)+h_neglect) / &
2551 (h(i,j,k-1)*h(i,j,k)+h_neglect2)) - &
2552 0.5*(ea(i,j,k) + eb(i,j,k-1))
2553 if (htot(i) < tr_ea_bbl)
then 2554 add_ent = max(0.0, add_ent, &
2555 (tr_ea_bbl - htot(i)) - min(ea(i,j,k), eb(i,j,k-1)))
2556 elseif (add_ent < 0.0)
then 2557 add_ent = 0.0 ; in_boundary(i) = .false.
2560 ebtr(i,j,k-1) = eb(i,j,k-1) + add_ent
2561 eatr(i,j,k) = ea(i,j,k) + add_ent
2563 ebtr(i,j,k-1) = eb(i,j,k-1) ; eatr(i,j,k) = ea(i,j,k)
2565 if (cs%double_diffuse)
then ;
if (kd_extra_s(i,j,k) > 0.0)
then 2566 add_ent = ((dt * kd_extra_s(i,j,k)) * gv%Z_to_H**2) / &
2567 (0.25 * ((h(i,j,k-1) + h(i,j,k)) + (hold(i,j,k-1) + hold(i,j,k))) + &
2569 ebtr(i,j,k-1) = ebtr(i,j,k-1) + add_ent
2570 eatr(i,j,k) = eatr(i,j,k) + add_ent
2573 do i=is,ie ; eatr(i,j,1) = ea(i,j,1) ;
enddo 2577 call call_tracer_column_fns(hold, h, eatr, ebtr, fluxes, hml, dt, g, gv, us, tv, &
2578 cs%optics, cs%tracer_flow_CSp, cs%debug)
2580 elseif (cs%double_diffuse)
then 2582 do j=js,je ;
do i=is,ie
2583 ebtr(i,j,nz) = eb(i,j,nz) ; eatr(i,j,1) = ea(i,j,1)
2586 do k=nz,2,-1 ;
do j=js,je ;
do i=is,ie
2587 if (kd_extra_s(i,j,k) > 0.0)
then 2588 add_ent = ((dt * kd_extra_s(i,j,k)) * gv%Z_to_H**2) / &
2589 (0.25 * ((h(i,j,k-1) + h(i,j,k)) + (hold(i,j,k-1) + hold(i,j,k))) + &
2594 ebtr(i,j,k-1) = eb(i,j,k-1) + add_ent
2595 eatr(i,j,k) = ea(i,j,k) + add_ent
2596 enddo ;
enddo ;
enddo 2598 call call_tracer_column_fns(hold, h, eatr, ebtr, fluxes, hml, dt, g, gv, us, tv, &
2599 cs%optics, cs%tracer_flow_CSp, cs%debug)
2602 call call_tracer_column_fns(hold, h, ea, eb, fluxes, hml, dt, g, gv, us, tv, &
2603 cs%optics, cs%tracer_flow_CSp, cs%debug)
2607 call cpu_clock_end(id_clock_tracers)
2610 if (cs%use_sponge)
then 2611 call cpu_clock_begin(id_clock_sponge)
2613 if (cs%bulkmixedlayer .and.
associated(tv%eqn_of_state))
then 2614 do i=is,ie ; p_ref_cv(i) = tv%P_Ref ;
enddo 2615 eosdom(:) = eos_domain(g%HI)
2618 call calculate_density(tv%T(:,j,1), tv%S(:,j,1), p_ref_cv, rcv_ml(:,j), &
2619 tv%eqn_of_state, eosdom)
2621 call apply_sponge(h, dt, g, gv, us, ea, eb, cs%sponge_CSp, rcv_ml)
2623 call apply_sponge(h, dt, g, gv, us, ea, eb, cs%sponge_CSp)
2625 call cpu_clock_end(id_clock_sponge)
2627 call mom_state_chksum(
"apply_sponge ", u, v, h, g, gv, us, haloshift=0)
2628 call mom_thermovar_chksum(
"apply_sponge ", tv, g)
2633 if (
associated(cdp%diapyc_vel))
then 2636 do k=2,nz ;
do i=is,ie
2637 cdp%diapyc_vel(i,j,k) = us%s_to_T*idt * (ea(i,j,k) - eb(i,j,k-1))
2640 cdp%diapyc_vel(i,j,1) = 0.0
2641 cdp%diapyc_vel(i,j,nz+1) = 0.0
2649 if (cs%bulkmixedlayer)
then 2651 call hchksum(ea,
"before net flux rearrangement ea", g%HI, scale=gv%H_to_m)
2652 call hchksum(eb,
"before net flux rearrangement eb", g%HI, scale=gv%H_to_m)
2656 do k=2,gv%nkml ;
do i=is,ie
2657 net_ent = ea(i,j,k) - eb(i,j,k-1)
2658 ea(i,j,k) = max(net_ent, 0.0)
2659 eb(i,j,k-1) = max(-net_ent, 0.0)
2663 call hchksum(ea,
"after net flux rearrangement ea", g%HI, scale=gv%H_to_m)
2664 call hchksum(eb,
"after net flux rearrangement eb", g%HI, scale=gv%H_to_m)
2672 hold(i,js-1,k) = gv%Angstrom_H ; ea(i,js-1,k) = 0.0 ; eb(i,js-1,k) = 0.0
2673 hold(i,je+1,k) = gv%Angstrom_H ; ea(i,je+1,k) = 0.0 ; eb(i,je+1,k) = 0.0
2676 hold(is-1,j,k) = gv%Angstrom_H ; ea(is-1,j,k) = 0.0 ; eb(is-1,j,k) = 0.0
2677 hold(ie+1,j,k) = gv%Angstrom_H ; ea(ie+1,j,k) = 0.0 ; eb(ie+1,j,k) = 0.0
2681 call cpu_clock_begin(id_clock_pass)
2682 if (g%symmetric)
then ; dir_flag = to_all+omit_corners
2683 else ; dir_flag = to_west+to_south+omit_corners ;
endif 2684 call create_group_pass(cs%pass_hold_eb_ea, hold, g%Domain, dir_flag, halo=1)
2685 call create_group_pass(cs%pass_hold_eb_ea, eb, g%Domain, dir_flag, halo=1)
2686 call create_group_pass(cs%pass_hold_eb_ea, ea, g%Domain, dir_flag, halo=1)
2687 call do_group_pass(cs%pass_hold_eb_ea, g%Domain)
2688 call cpu_clock_end(id_clock_pass)
2694 call mom_state_chksum(
"before u/v tridiag ", u, v, h, g, gv, us, haloshift=0)
2695 call hchksum(ea,
"before u/v tridiag ea", g%HI, scale=gv%H_to_m)
2696 call hchksum(eb,
"before u/v tridiag eb", g%HI, scale=gv%H_to_m)
2697 call hchksum(hold,
"before u/v tridiag hold", g%HI, scale=gv%H_to_m)
2699 call cpu_clock_begin(id_clock_tridiag)
2700 idt_accel = 1.0 / dt
2704 if (
associated(adp%du_dt_dia)) adp%du_dt_dia(i,j,1) = u(i,j,1)
2705 hval = (hold(i,j,1) + hold(i+1,j,1)) + (ea(i,j,1) + ea(i+1,j,1)) + h_neglect
2706 b1(i) = 1.0 / (hval + (eb(i,j,1) + eb(i+1,j,1)))
2707 d1(i) = hval * b1(i)
2708 u(i,j,1) = b1(i) * (hval * u(i,j,1))
2710 do k=2,nz ;
do i=isq,ieq
2711 if (
associated(adp%du_dt_dia)) adp%du_dt_dia(i,j,k) = u(i,j,k)
2712 c1(i,k) = (eb(i,j,k-1)+eb(i+1,j,k-1)) * b1(i)
2713 eaval = ea(i,j,k) + ea(i+1,j,k)
2714 hval = hold(i,j,k) + hold(i+1,j,k) + h_neglect
2715 b1(i) = 1.0 / ((eb(i,j,k) + eb(i+1,j,k)) + (hval + d1(i)*eaval))
2716 d1(i) = (hval + d1(i)*eaval) * b1(i)
2717 u(i,j,k) = (hval*u(i,j,k) + eaval*u(i,j,k-1))*b1(i)
2719 do k=nz-1,1,-1 ;
do i=isq,ieq
2720 u(i,j,k) = u(i,j,k) + c1(i,k+1)*u(i,j,k+1)
2721 if (
associated(adp%du_dt_dia)) &
2722 adp%du_dt_dia(i,j,k) = (u(i,j,k) - adp%du_dt_dia(i,j,k)) * idt_accel
2724 if (
associated(adp%du_dt_dia))
then 2726 adp%du_dt_dia(i,j,nz) = (u(i,j,nz)-adp%du_dt_dia(i,j,nz)) * idt_accel
2731 call mom_state_chksum(
"aft 1st loop tridiag ", u, v, h, g, gv, us, haloshift=0)
2736 if (
associated(adp%dv_dt_dia)) adp%dv_dt_dia(i,j,1) = v(i,j,1)
2737 hval = (hold(i,j,1) + hold(i,j+1,1)) + (ea(i,j,1) + ea(i,j+1,1)) + h_neglect
2738 b1(i) = 1.0 / (hval + (eb(i,j,1) + eb(i,j+1,1)))
2739 d1(i) = hval * b1(i)
2740 v(i,j,1) = b1(i) * (hval * v(i,j,1))
2742 do k=2,nz ;
do i=is,ie
2743 if (
associated(adp%dv_dt_dia)) adp%dv_dt_dia(i,j,k) = v(i,j,k)
2744 c1(i,k) = (eb(i,j,k-1)+eb(i,j+1,k-1)) * b1(i)
2745 eaval = ea(i,j,k) + ea(i,j+1,k)
2746 hval = hold(i,j,k) + hold(i,j+1,k) + h_neglect
2747 b1(i) = 1.0 / ((eb(i,j,k) + eb(i,j+1,k)) + (hval + d1(i)*eaval))
2748 d1(i) = (hval + d1(i)*eaval) * b1(i)
2749 v(i,j,k) = (hval*v(i,j,k) + eaval*v(i,j,k-1))*b1(i)
2751 do k=nz-1,1,-1 ;
do i=is,ie
2752 v(i,j,k) = v(i,j,k) + c1(i,k+1)*v(i,j,k+1)
2753 if (
associated(adp%dv_dt_dia)) &
2754 adp%dv_dt_dia(i,j,k) = (v(i,j,k) - adp%dv_dt_dia(i,j,k)) * idt_accel
2756 if (
associated(adp%dv_dt_dia))
then 2758 adp%dv_dt_dia(i,j,nz) = (v(i,j,nz)-adp%dv_dt_dia(i,j,nz)) * idt_accel
2762 call cpu_clock_end(id_clock_tridiag)
2764 call mom_state_chksum(
"after u/v tridiag ", u, v, h, g, gv, us, haloshift=0)
2767 call disable_averaging(cs%diag)
2769 call enable_averages(dt, time_end, cs%diag)
2771 if (cs%id_Kd_interface > 0)
call post_data(cs%id_Kd_interface, kd_int, cs%diag)
2772 if (cs%id_Kd_heat > 0)
call post_data(cs%id_Kd_heat, kd_heat, cs%diag)
2773 if (cs%id_Kd_salt > 0)
call post_data(cs%id_Kd_salt, kd_salt, cs%diag)
2774 if (cs%id_Kd_ePBL > 0)
call post_data(cs%id_Kd_ePBL, kd_epbl, cs%diag)
2776 if (cs%id_ea > 0)
call post_data(cs%id_ea, ea, cs%diag)
2777 if (cs%id_eb > 0)
call post_data(cs%id_eb, eb, cs%diag)
2779 if (cs%id_dudt_dia > 0)
call post_data(cs%id_dudt_dia, adp%du_dt_dia, cs%diag)
2780 if (cs%id_dvdt_dia > 0)
call post_data(cs%id_dvdt_dia, adp%dv_dt_dia, cs%diag)
2781 if (cs%id_wd > 0)
call post_data(cs%id_wd, cdp%diapyc_vel, cs%diag)
2783 if (cs%id_Tdif > 0)
call post_data(cs%id_Tdif, tdif_flx, cs%diag)
2784 if (cs%id_Tadv > 0)
call post_data(cs%id_Tadv, tadv_flx, cs%diag)
2785 if (cs%id_Sdif > 0)
call post_data(cs%id_Sdif, sdif_flx, cs%diag)
2786 if (cs%id_Sadv > 0)
call post_data(cs%id_Sadv, sadv_flx, cs%diag)
2789 if (cs%id_hf_dudt_dia_2d > 0)
then 2790 allocate(hf_dudt_dia_2d(g%IsdB:g%IedB,g%jsd:g%jed))
2791 hf_dudt_dia_2d(:,:) = 0.0
2792 do k=1,nz ;
do j=js,je ;
do i=isq,ieq
2793 hf_dudt_dia_2d(i,j) = hf_dudt_dia_2d(i,j) + adp%du_dt_dia(i,j,k) * adp%diag_hfrac_u(i,j,k)
2794 enddo ;
enddo ;
enddo 2795 call post_data(cs%id_hf_dudt_dia_2d, hf_dudt_dia_2d, cs%diag)
2796 deallocate(hf_dudt_dia_2d)
2799 if (cs%id_hf_dvdt_dia_2d > 0)
then 2800 allocate(hf_dvdt_dia_2d(g%isd:g%ied,g%JsdB:g%JedB))
2801 hf_dvdt_dia_2d(:,:) = 0.0
2802 do k=1,nz ;
do j=jsq,jeq ;
do i=is,ie
2803 hf_dvdt_dia_2d(i,j) = hf_dvdt_dia_2d(i,j) + adp%dv_dt_dia(i,j,k) * adp%diag_hfrac_v(i,j,k)
2804 enddo ;
enddo ;
enddo 2805 call post_data(cs%id_hf_dvdt_dia_2d, hf_dvdt_dia_2d, cs%diag)
2806 deallocate(hf_dvdt_dia_2d)
2809 call disable_averaging(cs%diag)
2811 if (showcalltree)
call calltree_leave(
"layered_diabatic()")