This subroutine determines the diffusivities from the integrated energetics mixed layer model. It assumes that heating, cooling and freshwater fluxes have already been applied. All calculations are done implicitly, and there is no stability limit on the time step.
237 type(ocean_grid_type),
intent(inout) :: g
238 type(verticalgrid_type),
intent(in) :: gv
239 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
240 intent(inout) :: h_3d
243 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
246 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
249 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
253 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
256 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
257 intent(in) :: tke_forced
260 type(thermo_var_ptrs),
intent(inout) :: tv
263 type(forcing),
intent(inout) :: fluxes
266 real,
intent(in) :: dt
267 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)+1), &
268 intent(out) :: kd_int
270 type(energetic_pbl_cs),
pointer :: cs
272 real,
dimension(SZI_(G),SZJ_(G)), &
273 intent(in) :: buoy_flux
274 real,
optional,
intent(in) :: dt_diag
277 logical,
optional,
intent(in) :: last_call
281 real,
dimension(SZI_(G),SZJ_(G),SZK_(GV)), &
282 optional,
intent(out) :: dt_expected, ds_expected
333 real,
dimension(SZI_(G),SZK_(GV)) :: &
339 real,
dimension(SZI_(G),SZK_(GV)+1) :: &
344 real,
dimension(SZI_(G)) :: &
361 real,
dimension(SZI_(G),SZK_(GV)) :: &
373 real,
dimension(SZK_(GV)) :: &
378 real,
dimension(SZK_(GV)) :: &
387 real,
dimension(SZI_(G)) :: &
391 real,
dimension(SZK_(GV)+1) :: &
451 real :: kd_guess0, pe_chg_g0, dpea_dkd_g0, kddt_h_g0
461 real :: tke_left_min, tke_left_max, kddt_h_max, kddt_h_min
469 logical :: convectively_stable
470 logical,
dimension(SZI_(G)) :: &
473 logical :: sfc_disconnect
479 real,
dimension(SZI_(G),SZJ_(G)) :: &
481 logical :: write_diags
482 logical :: reset_diags
485 real :: dtke_conv, dtke_forcing, dtke_mixing
486 real :: dtke_mke, dtke_mech_decay, dtke_conv_decay
490 real :: mld_guess, mld_found
491 real :: max_mld, min_mld
512 logical :: obl_converged
515 integer :: max_obl_it=20
524 real,
dimension(SZK_(GV)+1) :: vstar_used, &
527 logical :: obl_it_stats=.false.
528 REAL :: itguess(20), itresult(20),itmax(20),itmin(20)
530 integer,
save :: maxit=0
531 integer,
save :: minit=1e8
532 integer,
save :: sumit=0
533 integer,
save :: numit=0
535 integer,
save :: converged
536 integer,
save :: notconverged
538 real :: n2_dissipation
546 real :: mld_o_obukhov_stab
547 real :: ekman_o_obukhov_stab
548 real :: mld_o_obukhov_un
549 real :: ekman_o_obukhov_un
553 real :: mld_over_stab
558 real :: mstar_conv_adj
559 real :: mstar_stab, mstar_rot
560 logical :: debug=.false.
562 real :: dpe_debug, mixing_debug, taux2, tauy2
563 real,
dimension(20) :: tke_left_itt, pe_chg_itt, kddt_h_itt, dpea_dkd_itt, mke_src_itt
564 real,
dimension(SZI_(G),SZK_(GV)) :: &
565 mech_tke_k, conv_perel_k
566 real,
dimension(SZK_(GV)) :: nstar_k
567 integer,
dimension(SZK_(GV)) :: num_itts
569 integer :: i, j, k, is, ie, js, je, nz, itt, max_itt
571 is = g%isc ; ie = g%iec ; js = g%jsc ; je = g%jec ; nz = gv%ke
573 if (.not.
associated(cs))
call mom_error(fatal,
"energetic_PBL: "//&
574 "Module must be initialized before it is used.")
576 if (.not.
ASSOCIATED(tv%eqn_of_state))
call mom_error(fatal, &
577 "energetic_PBL: Temperature, salinity and an equation of state "//&
579 if (.NOT.
ASSOCIATED(fluxes%ustar))
call mom_error(fatal, &
580 "energetic_PBL: No surface TKE fluxes (ustar) defined in mixedlayer!")
581 if (
present(dt_expected) .or.
present(ds_expected)) debug = .true.
583 h_neglect = gv%H_subroundoff
585 if(.not.cs%Use_MLD_Iteration) max_obl_it=1
587 dt__diag = dt ;
if (
present(dt_diag)) dt__diag = dt_diag
588 idtdr0 = 1.0 / (dt__diag * gv%Rho0)
589 write_diags = .true. ;
if (
present(last_call)) write_diags = last_call
595 i_dtrho = 0.0 ;
if (dt*gv%Rho0 > 0.0) i_dtrho = 1.0 / (dt*gv%Rho0)
599 if (
present(dt_diag) .and. write_diags .and. (dt__diag > dt)) &
600 reset_diags = .false.
602 if (reset_diags)
then 604 if (cs%TKE_diagnostics)
then 606 do j=js,je ;
do i=is,ie
607 cs%diag_TKE_wind(i,j) = 0.0 ; cs%diag_TKE_MKE(i,j) = 0.0
608 cs%diag_TKE_conv(i,j) = 0.0 ; cs%diag_TKE_forcing(i,j) = 0.0
609 cs%diag_TKE_mixing(i,j) = 0.0 ; cs%diag_TKE_mech_decay(i,j) = 0.0
610 cs%diag_TKE_conv_decay(i,j) = 0.0
613 if (cs%Mixing_Diagnostics)
then 614 cs%Mixing_Length(:,:,:) = 0.0
615 cs%Velocity_Scale(:,:,:) = 0.0
652 do k=1,nz ;
do i=is,ie
653 h(i,k) = h_3d(i,j,k) + h_neglect ; u(i,k) = u_3d(i,j,k) ; v(i,k) = v_3d(i,j,k)
654 t(i,k) = tv%T(i,j,k) ; s(i,k) = tv%S(i,j,k)
658 cs%ML_depth(i,j) = h(i,1)*gv%H_to_m
660 sfc_connected(i) = .true.
664 mech_tke_k(:,:) = 0.0 ; conv_perel_k(:,:) = 0.0
673 do i=is,ie ;
if (g%mask2dT(i,j) > 0.5)
then 676 u_star = fluxes%ustar(i,j)
678 if ((g%mask2dCu(i-1,j) + g%mask2dCu(i,j)) > 0) &
679 taux2 = (g%mask2dCu(i-1,j)*fluxes%taux(i-1,j)**2 + &
680 g%mask2dCu(i,j)*fluxes%taux(i,j)**2) / (g%mask2dCu(i-1,j) + g%mask2dCu(i,j))
682 if ((g%mask2dCv(i,j-1) + g%mask2dCv(i,j)) > 0) &
683 tauy2 = (g%mask2dCv(i,j-1)*fluxes%tauy(i,j-1)**2 + &
684 g%mask2dCv(i,j)*fluxes%tauy(i,j)**2) / (g%mask2dCv(i,j-1) + g%mask2dCv(i,j))
685 u_star_mean = sqrt(sqrt(taux2 + tauy2)/gv%rho0)
686 if (
associated(fluxes%ustar_shelf) .and.
associated(fluxes%frac_shelf_h))
then 687 if (fluxes%frac_shelf_h(i,j) > 0.0) &
688 u_star = (1.0 - fluxes%frac_shelf_h(i,j)) * u_star + &
689 fluxes%frac_shelf_h(i,j) * fluxes%ustar_shelf(i,j)
691 if (u_star < cs%ustar_min) u_star = cs%ustar_min
693 bf_stable = max(0.0,buoy_flux(i,j))
694 bf_unstable = min(0.0,buoy_flux(i,j))
695 if (cs%omega_frac >= 1.0)
then ; absf(i) = 2.0*cs%omega
697 absf(i) = 0.25*((abs(g%CoriolisBu(i,j)) + abs(g%CoriolisBu(i-1,j-1))) + &
698 (abs(g%CoriolisBu(i,j-1)) + abs(g%CoriolisBu(i-1,j))))
699 if (cs%omega_frac > 0.0) &
700 absf(i) = sqrt(cs%omega_frac*4.0*cs%omega**2 + (1.0-cs%omega_frac)*absf(i)**2)
704 stab_scale = u_star**2 / ( vonkar * ( c_mo * bf_stable/u_star - c_ek * u_star * absf(i)))
706 il_ekman = absf(i)/u_star
707 il_obukhov = buoy_flux(i,j)*vonkar/u_star**3
709 if (cs%Mstar_Mode.eq.cs%CONST_MSTAR)
then 710 mech_tke(i) = (dt*cs%mstar*gv%Rho0)*((u_star**3))
713 if (cs%TKE_diagnostics)
then 714 cs%diag_TKE_wind(i,j) = cs%diag_TKE_wind(i,j) + mech_tke(i) * idtdr0
715 if (tke_forced(i,j,1) <= 0.0)
then 716 cs%diag_TKE_forcing(i,j) = cs%diag_TKE_forcing(i,j) + &
717 max(-mech_tke(i), tke_forced(i,j,1)) * idtdr0
721 cs%diag_TKE_forcing(i,j) = cs%diag_TKE_forcing(i,j) + cs%nstar*tke_forced(i,j,1) * idtdr0
725 if (tke_forced(i,j,1) <= 0.0)
then 726 mech_tke(i) = mech_tke(i) + tke_forced(i,j,1)
727 if (mech_tke(i) < 0.0) mech_tke(i) = 0.0
729 conv_perel(i) = conv_perel(i) + tke_forced(i,j,1)
738 h_sum(i) = h_neglect ;
do k=1,nz ; h_sum(i) = h_sum(i) + h(i,k) ;
enddo 739 i_hs = 0.0 ;
if (h_sum(i) > 0.0) i_hs = 1.0 / h_sum(i)
741 h_bot = 0.0 ; hb_hs(i,nz+1) = 0.0
743 h_bot = h_bot + h(i,k)
744 hb_hs(i,k) = h_bot * i_hs
749 dmass = gv%H_to_kg_m2 * h(i,k)
750 dpres = gv%g_Earth * dmass
751 dt_to_dpe(i,k) = (dmass * (pres(i,k) + 0.5*dpres)) * dsv_dt(i,j,k)
752 ds_to_dpe(i,k) = (dmass * (pres(i,k) + 0.5*dpres)) * dsv_ds(i,j,k)
753 dt_to_dcolht(i,k) = dmass * dsv_dt(i,j,k)
754 ds_to_dcolht(i,k) = dmass * dsv_ds(i,j,k)
756 pres(i,k+1) = pres(i,k) + dpres
763 do k=1,nz ; t0(k) = t(i,k) ; s0(k) = s(i,k) ;
enddo 767 mech_tke_top(i) = mech_tke(i) ; conv_perel_top(i) = conv_perel(i)
772 max_mld = 0.0 ;
do k=1,nz ; max_mld = max_mld + h(i,k)*gv%H_to_m ;
enddo 779 if (cs%MLD_iteration_guess .and. cs%ML_Depth2(i,j) > 1.)
then 781 mld_guess=cs%ML_Depth2(i,j)
784 mld_guess = 0.5 * (min_mld+max_mld)
788 obl_converged = .false.
792 do obl_it=1,max_obl_it ;
if (.not. obl_converged)
then 795 cs%ML_depth(i,j) = h(i,1)*gv%H_to_m
798 sfc_connected(i) = .true.
800 if (cs%Mstar_Mode.gt.0)
then 803 if (cs%MSTAR_MODE.eq.cs%MLD_o_OBUKHOV)
then 804 mld_over_stab = mld_guess / stab_scale - cs%MSTAR_XINT
805 if ((mld_over_stab) .le. 0.0)
then 807 mstar_mix = (cs%MSTAR_B*(mld_over_stab)+cs%MSTAR_A)**(cs%MSTAR_N)
809 if (cs%MSTAR_CAP>=0.)
then 810 if (cs%MSTAR_FLATCAP .OR. (mld_over_stab .le.cs%MSTAR_XINT_UP))
then 813 mstar_mix = min(cs%MSTAR_CAP, &
814 cs%MSTAR_SLOPE*(mld_over_stab)+cs%MSTAR_AT_XINT)
817 mstar_mix = cs%MSTAR_CAP - &
818 (cs%MSTAR_B2*(mld_over_stab-cs%MSTAR_XINT_UP)&
819 +cs%MSTAR_A2)**(cs%MSTAR_N)
823 mstar_mix = cs%MSTAR_SLOPE*(mld_over_stab)+cs%MSTAR_AT_XINT
826 elseif (cs%MSTAR_MODE.eq.cs%EKMAN_o_OBUKHOV)
then 827 mstar_stab = cs%MSTAR_COEF*sqrt(bf_stable/u_star**2/(absf(i)+1.e-10))
828 mstar_rot = cs%C_EK*log(max(1.,u_star/(absf(i)+1.e-10)/mld_guess))
829 if ( cs%MSTAR_CAP.le.0.0)
then 830 mstar_mix = max(mstar_stab,&
851 mstar_conv_adj = 1. - cs%CNV_MST_FAC * (-bf_unstable+1.e-10) / &
852 ( (-bf_unstable+1.e-10)+ &
853 2. *mstar_mix *u_star**3 / mld_guess )
854 if (cs%Use_LA_windsea)
then 856 call get_la_windsea( u_star_mean, mld_guess*cs%LaDepthRatio, gv, la)
858 mld_o_ekman = abs(mld_guess*il_ekman)
859 mld_o_obukhov_stab = abs(max(0.,mld_guess*il_obukhov))
860 mld_o_obukhov_un = abs(min(0.,mld_guess*il_obukhov))
861 ekman_o_obukhov_stab = abs(max(0.,il_obukhov/(il_ekman+1.e-10)))
862 ekman_o_obukhov_un = abs(min(0.,il_obukhov/(il_ekman+1.e-10)))
866 lamod = la * (1.0 + max(-0.5,cs%LaC_MLDoEK * mld_o_ekman) + &
867 cs%LaC_EKoOB_stab * ekman_o_obukhov_stab + &
868 cs%LaC_EKoOB_un * ekman_o_obukhov_un + &
869 cs%LaC_MLDoOB_stab * mld_o_obukhov_stab + &
870 cs%LaC_MLDoOB_un * mld_o_obukhov_un )
871 if (cs%LT_Enhance_Form==1)
then 873 enhance_m = (1+(1.4*la)**(-2)+(5.4*la)**(-4))**(1.5)
874 elseif (cs%LT_Enhance_Form==2)
then 876 enhance_m = min(cs%Max_Enhance_M,(1.+cs%LT_ENHANCE_COEF*lamod**cs%LT_ENHANCE_EXP))
878 elseif (cs%LT_ENHANCE_Form == 3)
then 880 mstar_lt = cs%LT_ENHANCE_COEF * lamod**cs%LT_ENHANCE_EXP
885 mech_tke(i) = ( mstar_mix * mstar_conv_adj * enhance_m + mstar_lt) * (dt*gv%Rho0*u_star**3)
887 if (cs%TKE_diagnostics)
then 888 cs%diag_TKE_wind(i,j) = cs%diag_TKE_wind(i,j) + mech_tke(i) * idtdr0
889 if (tke_forced(i,j,1) <= 0.0)
then 890 cs%diag_TKE_forcing(i,j) = cs%diag_TKE_forcing(i,j) + &
891 max(-mech_tke(i), tke_forced(i,j,1)) * idtdr0
895 cs%diag_TKE_forcing(i,j) = cs%diag_TKE_forcing(i,j) + cs%nstar*tke_forced(i,j,1) * idtdr0
899 if (tke_forced(i,j,1) <= 0.0)
then 900 mech_tke(i) = mech_tke(i) + tke_forced(i,j,1)
901 if (mech_tke(i) < 0.0) mech_tke(i) = 0.0
903 conv_perel(i) = conv_perel(i) + tke_forced(i,j,1)
906 mech_tke(i) = mech_tke_top(i)*enhance_m ; conv_perel(i) = conv_perel_top(i)
909 if (cs%TKE_diagnostics)
then 910 dtke_conv = 0.0 ; dtke_forcing = 0.0 ; dtke_mixing = 0.0
911 dtke_mke = 0.0 ; dtke_mech_decay = 0.0 ; dtke_conv_decay = 0.0
917 vstar_used(k) = 0.0 ; mixing_length_used(k) = 0.0
919 if (.not.cs%Use_MLD_Iteration) obl_converged = .true.
921 if ((.not.cs%Use_MLD_Iteration) .or. &
922 (cs%transLay_scale >= 1.0) .or. (cs%transLay_scale < 0.0) )
then 923 do k=1,nz+1 ; mixlen_shape(k) = 1.0 ;
enddo 924 elseif (mld_guess <= 0.0)
then 925 if (cs%transLay_scale > 0.0)
then 926 do k=1,nz+1 ; mixlen_shape(k) = cs%transLay_scale ;
enddo 928 do k=1,nz+1 ; mixlen_shape(k) = 1.0 ;
enddo 933 i_mld = 1.0 / mld_guess ; h_rsum = 0.0
934 mixlen_shape(1) = 1.0
936 h_rsum = h_rsum + h(i,k-1)
937 if (cs%MixLenExponent==2.0)
then 938 mixlen_shape(k) = cs%transLay_scale + (1.0 - cs%transLay_scale) * &
939 (max(0.0, (mld_guess - h_rsum)*i_mld) )**2
941 mixlen_shape(k) = cs%transLay_scale + (1.0 - cs%transLay_scale) * &
942 (max(0.0, (mld_guess - h_rsum)*i_mld) )**cs%MixLenExponent
948 kd(i,1) = 0.0 ; kddt_h(1) = 0.0
950 dt_to_dpe_a(i,1) = dt_to_dpe(i,1) ; dt_to_dcolht_a(i,1) = dt_to_dcolht(i,1)
951 ds_to_dpe_a(i,1) = ds_to_dpe(i,1) ; ds_to_dcolht_a(i,1) = ds_to_dcolht(i,1)
953 htot(i) = h(i,1) ; uhtot(i) = u(i,1)*h(i,1) ; vhtot(i) = v(i,1)*h(i,1)
956 mech_tke_k(i,1) = mech_tke(i) ; conv_perel_k(i,1) = conv_perel(i)
957 nstar_k(:) = 0.0 ; nstar_k(1) = cs%nstar ; num_itts(:) = -1
968 idecay_len_tke(i) = (cs%TKE_decay * absf(i) / u_star) * gv%H_to_m
970 if (idecay_len_tke(i) > 0.0) exp_kh = exp(-h(i,k-1)*idecay_len_tke(i))
971 if (cs%TKE_diagnostics) &
972 dtke_mech_decay = dtke_mech_decay + (exp_kh-1.0) * mech_tke(i) * idtdr0
973 mech_tke(i) = mech_tke(i) * exp_kh
977 if (tke_forced(i,j,k) > 0.0)
then 978 conv_perel(i) = conv_perel(i) + tke_forced(i,j,k)
979 if (cs%TKE_diagnostics) &
980 dtke_forcing = dtke_forcing + cs%nstar*tke_forced(i,j,k) * idtdr0
984 mech_tke_k(i,k) = mech_tke(i) ; conv_perel_k(i,k) = conv_perel(i)
989 if (cs%nstar * conv_perel(i) > 0.0)
then 993 nstar_fc = cs%nstar * conv_perel(i) / (conv_perel(i) + 0.2 * &
994 sqrt(0.5 * dt * gv%Rho0 * (absf(i)*(htot(i)*gv%H_to_m))**3 * conv_perel(i)))
996 if (debug) nstar_k(k) = nstar_fc
998 tot_tke = mech_tke(i) + nstar_fc * conv_perel(i)
1002 if (tke_forced(i,j,k) < 0.0)
then 1003 if (tke_forced(i,j,k) + tot_tke < 0.0)
then 1005 if (cs%TKE_diagnostics)
then 1006 dtke_mixing = dtke_mixing + tot_tke * idtdr0
1007 dtke_forcing = dtke_forcing - tot_tke * idtdr0
1010 dtke_conv_decay = dtke_conv_decay + &
1011 (cs%nstar-nstar_fc) * conv_perel(i) * idtdr0
1013 tot_tke = 0.0 ; mech_tke(i) = 0.0 ; conv_perel(i) = 0.0
1016 tke_reduc = (tot_tke + tke_forced(i,j,k)) / tot_tke
1017 if (cs%TKE_diagnostics)
then 1018 dtke_mixing = dtke_mixing - tke_forced(i,j,k) * idtdr0
1019 dtke_forcing = dtke_forcing + tke_forced(i,j,k) * idtdr0
1020 dtke_conv_decay = dtke_conv_decay + &
1021 (1.0-tke_reduc)*(cs%nstar-nstar_fc) * conv_perel(i) * idtdr0
1023 tot_tke = tke_reduc*tot_tke
1024 mech_tke(i) = tke_reduc*mech_tke(i)
1025 conv_perel(i) = tke_reduc*conv_perel(i)
1030 if (cs%orig_PE_calc)
then 1032 dte_t2 = 0.0 ; dse_t2 = 0.0
1034 dte_t2 = kddt_h(k-1) * ((t0(k-2) - t0(k-1)) + dte(k-2))
1035 dse_t2 = kddt_h(k-1) * ((s0(k-2) - s0(k-1)) + dse(k-2))
1038 dt_h = (gv%m_to_H**2*dt) / max(0.5*(h(i,k-1)+h(i,k)), 1e-15*h_sum(i))
1046 convectively_stable = ( 0.0 <= &
1047 ( (dt_to_dcolht(i,k) + dt_to_dcolht(i,k-1) ) * (t0(k-1)-t0(k)) + &
1048 (ds_to_dcolht(i,k) + ds_to_dcolht(i,k-1) ) * (s0(k-1)-s0(k)) ) )
1050 if ((mech_tke(i) + conv_perel(i)) <= 0.0 .and. convectively_stable)
then 1052 tot_tke = 0.0 ; mech_tke(i) = 0.0 ; conv_perel(i) = 0.0
1053 kd(i,k) = 0.0 ; kddt_h(k) = 0.0
1054 sfc_disconnect = .true.
1064 if (cs%orig_PE_calc)
then 1065 dte(k-1) = b1 * ( dte_t2 )
1066 dse(k-1) = b1 * ( dse_t2 )
1070 dt_to_dpe_a(i,k) = dt_to_dpe(i,k)
1071 ds_to_dpe_a(i,k) = ds_to_dpe(i,k)
1072 dt_to_dcolht_a(i,k) = dt_to_dcolht(i,k)
1073 ds_to_dcolht_a(i,k) = ds_to_dcolht(i,k)
1076 sfc_disconnect = .false.
1080 if (cs%orig_PE_calc)
then 1082 dt_km1_t2 = (t0(k)-t0(k-1))
1083 ds_km1_t2 = (s0(k)-s0(k-1))
1085 dt_km1_t2 = (t0(k)-t0(k-1)) - &
1086 (kddt_h(k-1) / hp_a(i)) * ((t0(k-2) - t0(k-1)) + dte(k-2))
1087 ds_km1_t2 = (s0(k)-s0(k-1)) - &
1088 (kddt_h(k-1) / hp_a(i)) * ((s0(k-2) - s0(k-1)) + dse(k-2))
1090 dte_term = dte_t2 + hp_a(i) * (t0(k-1)-t0(k))
1091 dse_term = dse_t2 + hp_a(i) * (s0(k-1)-s0(k))
1094 th_a(k-1) = h(i,k-1) * t0(k-1) ; sh_a(k-1) = h(i,k-1) * s0(k-1)
1096 th_a(k-1) = h(i,k-1) * t0(k-1) + kddt_h(k-1) * te(k-2)
1097 sh_a(k-1) = h(i,k-1) * s0(k-1) + kddt_h(k-1) * se(k-2)
1099 th_b(k) = h(i,k) * t0(k) ; sh_b(k) = h(i,k) * s0(k)
1107 if ((cs%MKE_to_TKE_effic > 0.0) .and. (htot(i)*h(i,k) > 0.0))
then 1110 dmke_max = (gv%H_to_kg_m2 * cs%MKE_to_TKE_effic) * 0.5 * &
1111 (h(i,k) / ((htot(i) + h(i,k))*htot(i))) * &
1112 ((uhtot(i)-u(i,k)*htot(i))**2 + (vhtot(i)-v(i,k)*htot(i))**2)
1115 mke2_hharm = (htot(i) + h(i,k) + 2.0*h_neglect) / &
1116 ((htot(i)+h_neglect) * (h(i,k)+h_neglect))
1118 dmke_max = 0.0 ; mke2_hharm = 0.0
1124 h_tt = htot(i) + h_tt_min
1125 tke_here = mech_tke(i) + cs%wstar_ustar_coef*conv_perel(i)
1126 if (tke_here > 0.0)
then 1127 vstar = cs%vstar_scale_fac * (i_dtrho*tke_here)**c1_3
1128 hbs_here = gv%H_to_m * min(hb_hs(i,k), mixlen_shape(k))
1129 mixing_length_used(k) = max(cs%min_mix_len,((h_tt*hbs_here)*vstar) / &
1130 ((cs%Ekman_scale_coef * absf(i)) * (h_tt*hbs_here) + vstar))
1133 if (.not.cs%Use_MLD_Iteration)
then 1134 kd_guess0 = vstar * vonkar * ((h_tt*hbs_here)*vstar) / &
1135 ((cs%Ekman_scale_coef * absf(i)) * (h_tt*hbs_here) + vstar)
1137 kd_guess0 = vstar * vonkar * mixing_length_used(k)
1140 vstar = 0.0 ; kd_guess0 = 0.0
1142 vstar_used(k) = vstar
1143 kddt_h_g0 = kd_guess0*dt_h
1145 if (cs%orig_PE_calc)
then 1146 call find_pe_chg_orig(kddt_h_g0, h(i,k), hp_a(i), dte_term, dse_term, &
1147 dt_km1_t2, ds_km1_t2, dt_to_dpe(i,k), ds_to_dpe(i,k), &
1148 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), &
1149 pres(i,k), dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1150 dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1151 pe_chg=pe_chg_g0, dpec_dkd=dpea_dkd_g0, dpe_max=pe_chg_max, &
1152 dpec_dkd_0=dpec_dkd_kd0 )
1154 call find_pe_chg(0.0, kddt_h_g0, hp_a(i), h(i,k), &
1155 th_a(k-1), sh_a(k-1), th_b(k), sh_b(k), &
1156 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), dt_to_dpe(i,k), ds_to_dpe(i,k), &
1157 pres(i,k), dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1158 dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1159 pe_chg=pe_chg_g0, dpec_dkd=dpea_dkd_g0, dpe_max=pe_chg_max, &
1160 dpec_dkd_0=dpec_dkd_kd0 )
1163 mke_src = dmke_max*(1.0 - exp(-kddt_h_g0 * mke2_hharm))
1165 if (pe_chg_g0 .gt. 0.0)
then 1167 n2_dissipation = 1.+cs%N2_DISSIPATION_SCALE_NEG
1170 n2_dissipation = 1.+cs%N2_DISSIPATION_SCALE_POS
1173 if ((pe_chg_g0 < 0.0) .or. ((vstar == 0.0) .and. (dpec_dkd_kd0 < 0.0)))
then 1175 if (pe_chg_max <= 0.0)
then 1177 tke_here = mech_tke(i) + cs%wstar_ustar_coef*(conv_perel(i)-pe_chg_max)
1178 if (tke_here > 0.0)
then 1179 vstar = cs%vstar_scale_fac * (i_dtrho*tke_here)**c1_3
1180 hbs_here = gv%H_to_m * min(hb_hs(i,k), mixlen_shape(k))
1181 mixing_length_used(k) = max(cs%min_mix_len,((h_tt*hbs_here)*vstar) / &
1182 ((cs%Ekman_scale_coef * absf(i)) * (h_tt*hbs_here) + vstar))
1183 if (.not.cs%Use_MLD_Iteration)
then 1186 kd(i,k) = vstar * vonkar * ((h_tt*hbs_here)*vstar) / &
1187 ((cs%Ekman_scale_coef * absf(i)) * (h_tt*hbs_here) + vstar)
1189 kd(i,k) = vstar * vonkar * mixing_length_used(k)
1192 vstar = 0.0 ; kd(i,k) = 0.0
1194 vstar_used(k) = vstar
1196 if (cs%orig_PE_calc)
then 1197 call find_pe_chg_orig(kd(i,k)*dt_h, h(i,k), hp_a(i), dte_term, dse_term, &
1198 dt_km1_t2, ds_km1_t2, dt_to_dpe(i,k), ds_to_dpe(i,k), &
1199 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), &
1200 pres(i,k), dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1201 dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1204 call find_pe_chg(0.0, kd(i,k)*dt_h, hp_a(i), h(i,k), &
1205 th_a(k-1), sh_a(k-1), th_b(k), sh_b(k), &
1206 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), dt_to_dpe(i,k), ds_to_dpe(i,k), &
1207 pres(i,k), dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1208 dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1212 if (dpe_conv > 0.0)
then 1213 kd(i,k) = kd_guess0 ; dpe_conv = pe_chg_g0
1215 mke_src = dmke_max*(1.0 - exp(-(kd(i,k)*dt_h) * mke2_hharm))
1219 kd(i,k) = kd_guess0 ; dpe_conv = pe_chg_g0
1221 conv_perel(i) = conv_perel(i) - dpe_conv
1222 mech_tke(i) = mech_tke(i) + mke_src
1223 if (cs%TKE_diagnostics)
then 1224 dtke_conv = dtke_conv - cs%nstar*dpe_conv * idtdr0
1225 dtke_mke = dtke_mke + mke_src * idtdr0
1227 if (sfc_connected(i))
then 1228 cs%ML_depth(i,j) = cs%ML_depth(i,j) + gv%H_to_m * h(i,k)
1232 kddt_h(k) = kd(i,k)*dt_h
1233 elseif (tot_tke + (mke_src - n2_dissipation*pe_chg_g0) >= 0.0)
then 1236 kddt_h(k) = kddt_h_g0
1239 tot_tke = tot_tke + mke_src
1241 if (tot_tke > 0.0) tke_reduc = (tot_tke - n2_dissipation*pe_chg_g0) &
1243 if (cs%TKE_diagnostics)
then 1244 dtke_mixing = dtke_mixing - pe_chg_g0 * idtdr0
1245 dtke_mke = dtke_mke + mke_src * idtdr0
1246 dtke_conv_decay = dtke_conv_decay + &
1247 (1.0-tke_reduc)*(cs%nstar-nstar_fc) * conv_perel(i) * idtdr0
1249 tot_tke = tke_reduc*tot_tke
1250 mech_tke(i) = tke_reduc*(mech_tke(i) + mke_src)
1251 conv_perel(i) = tke_reduc*conv_perel(i)
1252 if (sfc_connected(i))
then 1253 cs%ML_depth(i,j) = cs%ML_depth(i,j) + gv%H_to_m * h(i,k)
1256 elseif (tot_tke == 0.0)
then 1258 kd(i,k) = 0.0 ; kddt_h(k) = 0.0
1259 tot_tke = 0.0 ; conv_perel(i) = 0.0 ; mech_tke(i) = 0.0
1260 sfc_disconnect = .true.
1264 kddt_h_max = kddt_h_g0 ; kddt_h_min = 0.0
1265 tke_left_max = tot_tke + (mke_src - n2_dissipation*pe_chg_g0) ;
1266 tke_left_min = tot_tke
1270 kddt_h_guess = tot_tke * kddt_h_max / max( n2_dissipation*pe_chg_g0 &
1271 - mke_src, kddt_h_max * (dpec_dkd_kd0 - dmke_max * &
1279 tke_left_itt(:) = 0.0 ; dpea_dkd_itt(:) = 0.0 ; pe_chg_itt(:) = 0.0
1280 mke_src_itt(:) = 0.0 ; kddt_h_itt(:) = 0.0
1283 if (cs%orig_PE_calc)
then 1284 call find_pe_chg_orig(kddt_h_guess, h(i,k), hp_a(i), dte_term, dse_term, &
1285 dt_km1_t2, ds_km1_t2, dt_to_dpe(i,k), ds_to_dpe(i,k), &
1286 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), &
1287 pres(i,k), dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1288 dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1289 pe_chg=pe_chg, dpec_dkd=dpec_dkd )
1291 call find_pe_chg(0.0, kddt_h_guess, hp_a(i), h(i,k), &
1292 th_a(k-1), sh_a(k-1), th_b(k), sh_b(k), &
1293 dt_to_dpe_a(i,k-1), ds_to_dpe_a(i,k-1), dt_to_dpe(i,k), ds_to_dpe(i,k), &
1294 pres(i,k), dt_to_dcolht_a(i,k-1), ds_to_dcolht_a(i,k-1), &
1295 dt_to_dcolht(i,k), ds_to_dcolht(i,k), &
1298 mke_src = dmke_max * (1.0 - exp(-mke2_hharm * kddt_h_guess))
1299 dmke_src_dk = dmke_max * mke2_hharm * exp(-mke2_hharm * kddt_h_guess)
1301 tke_left = tot_tke + (mke_src - n2_dissipation*pe_chg)
1303 kddt_h_itt(itt) = kddt_h_guess ; mke_src_itt(itt) = mke_src
1304 pe_chg_itt(itt) = n2_dissipation*pe_chg
1305 tke_left_itt(itt) = tke_left
1306 dpea_dkd_itt(itt) = dpec_dkd
1310 if (tke_left >= 0.0)
then 1311 kddt_h_min = kddt_h_guess ; tke_left_min = tke_left
1313 kddt_h_max = kddt_h_guess ; tke_left_max = tke_left
1319 if (dpec_dkd*n2_dissipation - dmke_src_dk <= 0.0)
then 1322 dkddt_h_newt = tke_left / (dpec_dkd*n2_dissipation - dmke_src_dk)
1323 kddt_h_newt = kddt_h_guess + dkddt_h_newt
1324 if ((kddt_h_newt > kddt_h_max) .or. (kddt_h_newt < kddt_h_min)) &
1329 kddt_h_next = kddt_h_guess + dkddt_h_newt
1330 dkddt_h = dkddt_h_newt
1332 kddt_h_next = (tke_left_max * kddt_h_min - kddt_h_max * tke_left_min) / &
1333 (tke_left_max - tke_left_min)
1334 dkddt_h = kddt_h_next - kddt_h_guess
1337 if ((abs(dkddt_h) < 1e-9*kddt_h_guess) .or. (itt==max_itt))
then 1339 if (debug) num_itts(k) = itt
1342 kddt_h_guess = kddt_h_next
1345 kd(i,k) = kddt_h_guess / dt_h ; kddt_h(k) = kd(i,k)*dt_h
1348 if (cs%TKE_diagnostics)
then 1349 dtke_mixing = dtke_mixing - (tot_tke + mke_src) * idtdr0
1350 dtke_mke = dtke_mke + mke_src * idtdr0
1351 dtke_conv_decay = dtke_conv_decay + &
1352 (cs%nstar-nstar_fc) * conv_perel(i) * idtdr0
1355 if (sfc_connected(i)) cs%ML_depth(i,j) = cs%ML_depth(i,j) + &
1356 (pe_chg / pe_chg_g0) * gv%H_to_m * h(i,k)
1357 tot_tke = 0.0 ; mech_tke(i) = 0.0 ; conv_perel(i) = 0.0
1358 sfc_disconnect = .true.
1361 kddt_h(k) = kd(i,k)*dt_h
1364 b1 = 1.0 / (hp_a(i) + kddt_h(k))
1365 c1(k) = kddt_h(k) * b1
1366 if (cs%orig_PE_calc)
then 1367 dte(k-1) = b1 * ( kddt_h(k)*(t0(k)-t0(k-1)) + dte_t2 )
1368 dse(k-1) = b1 * ( kddt_h(k)*(s0(k)-s0(k-1)) + dse_t2 )
1371 hp_a(i) = h(i,k) + (hp_a(i) * b1) * kddt_h(k)
1372 dt_to_dpe_a(i,k) = dt_to_dpe(i,k) + c1(k)*dt_to_dpe_a(i,k-1)
1373 ds_to_dpe_a(i,k) = ds_to_dpe(i,k) + c1(k)*ds_to_dpe_a(i,k-1)
1374 dt_to_dcolht_a(i,k) = dt_to_dcolht(i,k) + c1(k)*dt_to_dcolht_a(i,k-1)
1375 ds_to_dcolht_a(i,k) = ds_to_dcolht(i,k) + c1(k)*ds_to_dcolht_a(i,k-1)
1380 if (sfc_disconnect)
then 1382 uhtot(i) = u(i,k)*h(i,k)
1383 vhtot(i) = v(i,k)*h(i,k)
1385 sfc_connected(i) = .false.
1387 uhtot(i) = uhtot(i) + u(i,k)*h(i,k)
1388 vhtot(i) = vhtot(i) + v(i,k)*h(i,k)
1389 htot(i) = htot(i) + h(i,k)
1394 te(1) = b1*(h(i,1)*t0(1))
1395 se(1) = b1*(h(i,1)*s0(1))
1397 te(k-1) = b1 * (h(i,k-1) * t0(k-1) + kddt_h(k-1) * te(k-2))
1398 se(k-1) = b1 * (h(i,k-1) * s0(k-1) + kddt_h(k-1) * se(k-2))
1407 te(nz) = b1 * (h(i,nz) * t0(nz) + kddt_h(nz) * te(nz-1))
1408 se(nz) = b1 * (h(i,nz) * s0(nz) + kddt_h(nz) * se(nz-1))
1410 te(k) = te(k) + c1(k+1)*te(k+1)
1411 se(k) = se(k) + c1(k+1)*se(k+1)
1414 if (
present(dt_expected))
then 1415 do k=1,nz ; dt_expected(i,j,k) = te(k) - t0(k) ;
enddo 1417 if (
present(ds_expected))
then 1418 do k=1,nz ; ds_expected(i,j,k) = se(k) - s0(k) ;
enddo 1423 dpe_debug = dpe_debug + (dt_to_dpe(i,k) * (te(k) - t0(k)) + &
1424 ds_to_dpe(i,k) * (se(k) - s0(k)))
1426 mixing_debug = dpe_debug * idtdr0
1436 itmax(obl_it) = max_mld
1437 itmin(obl_it) = min_mld
1438 itguess(obl_it) = mld_guess
1440 mld_found=0.0 ; first_obl=.true.
1441 if (cs%Orig_MLD_iteration)
then 1445 if (vstar_used(k) > 1.e-10 .and. k < nz)
then 1446 mld_found = mld_found+h(i,k-1)*gv%H_to_m
1449 if (mld_found-cs%MLD_tol > mld_guess)
then 1451 elseif ((mld_guess-mld_found) < max(cs%MLD_tol,h(i,k-1)*gv%H_to_m))
then 1452 obl_converged = .true.
1453 if (obl_it_stats)
then 1454 maxit = max(maxit,obl_it)
1455 minit = min(minit,obl_it)
1456 sumit = sumit+obl_it
1458 print*,maxit,minit,sumit/numit
1460 cs%ML_Depth2(i,j) = mld_guess
1469 mld_found=cs%ML_DEPTH(i,j)
1470 if (mld_found-cs%MLD_tol > mld_guess)
then 1472 elseif (abs(mld_guess-mld_found) < (cs%MLD_tol))
then 1473 obl_converged = .true.
1474 if (obl_it_stats)
then 1475 maxit = max(maxit,obl_it)
1476 minit = min(minit,obl_it)
1477 sumit = sumit+obl_it
1479 print*,maxit,minit,sumit/numit
1481 cs%ML_Depth2(i,j) = mld_guess
1487 mld_guess = min_mld*0.5 + max_mld*0.5
1488 itresult(obl_it) = mld_found
1490 if (.not.obl_converged)
then 1494 notconverged=notconverged+1
1508 converged=converged+1
1511 if (cs%TKE_diagnostics)
then 1512 cs%diag_TKE_MKE(i,j) = cs%diag_TKE_MKE(i,j) + dtke_mke
1513 cs%diag_TKE_conv(i,j) = cs%diag_TKE_conv(i,j) + dtke_conv
1514 cs%diag_TKE_forcing(i,j) = cs%diag_TKE_forcing(i,j) + dtke_forcing
1515 cs%diag_TKE_mixing(i,j) = cs%diag_TKE_mixing(i,j) + dtke_mixing
1516 cs%diag_TKE_mech_decay(i,j) = cs%diag_TKE_mech_decay(i,j) + dtke_mech_decay
1517 cs%diag_TKE_conv_decay(i,j) = cs%diag_TKE_conv_decay(i,j) + dtke_conv_decay
1520 if (cs%Mixing_Diagnostics)
then 1524 cs%Mixing_Length(i,j,k) = mixing_length_used(k)
1525 cs%Velocity_Scale(i,j,k) = vstar_used(k)
1528 if (
allocated(cs%Enhance_M)) cs%Enhance_M(i,j) = enhance_m
1529 if (
allocated(cs%mstar_mix)) cs%mstar_mix(i,j) = mstar_mix
1530 if (
allocated(cs%MLD_Obukhov)) cs%MLD_Obukhov(i,j) = (mld_guess*il_obukhov)
1531 if (
allocated(cs%MLD_Ekman)) cs%MLD_Ekman(i,j) = (mld_guess*il_ekman)
1532 if (
allocated(cs%Ekman_Obukhov)) cs%Ekman_Obukhov(i,j) = (il_obukhov/(il_ekman+1.e-10))
1533 if (
allocated(cs%La)) cs%La(i,j) = la
1534 if (
allocated(cs%La_mod)) cs%La_mod(i,j) = lamod
1540 if (
present(dt_expected))
then 1541 do k=1,nz ; dt_expected(i,j,k) = 0.0 ;
enddo 1543 if (
present(ds_expected))
then 1544 do k=1,nz ; ds_expected(i,j,k) = 0.0 ;
enddo 1548 if (cs%id_Hsfc_used > 0)
then 1549 do i=is,ie ; hsfc_used(i,j) = h(i,1)*gv%H_to_m ;
enddo 1550 do k=2,nz ;
do i=is,ie
1551 if (kd(i,k) > 0.0) hsfc_used(i,j) = hsfc_used(i,j) + h(i,k)*gv%H_to_m
1555 do k=1,nz+1 ;
do i=is,ie
1556 kd_int(i,j,k) = kd(i,k)
1561 if (write_diags)
then 1562 if (cs%id_ML_depth > 0) &
1563 call post_data(cs%id_ML_depth, cs%ML_depth, cs%diag)
1564 if (cs%id_TKE_wind > 0) &
1565 call post_data(cs%id_TKE_wind, cs%diag_TKE_wind, cs%diag)
1566 if (cs%id_TKE_MKE > 0) &
1567 call post_data(cs%id_TKE_MKE, cs%diag_TKE_MKE, cs%diag)
1568 if (cs%id_TKE_conv > 0) &
1569 call post_data(cs%id_TKE_conv, cs%diag_TKE_conv, cs%diag)
1570 if (cs%id_TKE_forcing > 0) &
1571 call post_data(cs%id_TKE_forcing, cs%diag_TKE_forcing, cs%diag)
1572 if (cs%id_TKE_mixing > 0) &
1573 call post_data(cs%id_TKE_mixing, cs%diag_TKE_mixing, cs%diag)
1574 if (cs%id_TKE_mech_decay > 0) &
1575 call post_data(cs%id_TKE_mech_decay, cs%diag_TKE_mech_decay, cs%diag)
1576 if (cs%id_TKE_conv_decay > 0) &
1577 call post_data(cs%id_TKE_conv_decay, cs%diag_TKE_conv_decay, cs%diag)
1578 if (cs%id_Hsfc_used > 0) &
1579 call post_data(cs%id_Hsfc_used, hsfc_used, cs%diag)
1580 if (cs%id_Mixing_Length > 0) &
1581 call post_data(cs%id_Mixing_Length, cs%Mixing_Length, cs%diag)
1582 if (cs%id_Velocity_Scale >0) &
1583 call post_data(cs%id_Velocity_Scale, cs%Velocity_Scale, cs%diag)
1584 if (cs%id_OSBL >0) &
1585 call post_data(cs%id_OSBL, cs%ML_Depth2, cs%diag)
1586 if (cs%id_LT_Enhancement >0) &
1587 call post_data(cs%id_LT_Enhancement, cs%Enhance_M, cs%diag)
1588 if (cs%id_MSTAR_MIX >0) &
1589 call post_data(cs%id_MSTAR_MIX, cs%MSTAR_MIX, cs%diag)
1590 if (cs%id_MLD_OBUKHOV >0) &
1591 call post_data(cs%id_MLD_Obukhov, cs%MLD_OBUKHOV, cs%diag)
1592 if (cs%id_MLD_EKMAN >0) &
1593 call post_data(cs%id_MLD_Ekman, cs%MLD_EKMAN, cs%diag)
1594 if (cs%id_Ekman_Obukhov >0) &
1595 call post_data(cs%id_Ekman_Obukhov, cs%Ekman_Obukhov, cs%diag)
1597 call post_data(cs%id_LA, cs%LA, cs%diag)
1598 if (cs%id_LA_MOD >0) &
1599 call post_data(cs%id_LA_MOD, cs%LA_MOD, cs%diag)