4 use esmf,
only: esmf_clock, esmf_clockget, esmf_time, esmf_timeget
5 use esmf,
only: esmf_timeinterval, esmf_timeintervalget
6 use esmf,
only: esmf_state, esmf_stateget
7 use esmf,
only: esmf_field, esmf_fieldget, esmf_fieldcreate
8 use esmf,
only: esmf_gridcomp, esmf_mesh, esmf_grid, esmf_gridcreate
9 use esmf,
only: esmf_distgrid, esmf_distgridcreate
10 use esmf,
only: esmf_kind_r8, esmf_success, esmf_logfounderror
11 use esmf,
only: esmf_logerr_passthru, esmf_logmsg_info, esmf_logwrite
12 use esmf,
only: esmf_logseterror, esmf_rc_mem_allocate
13 use esmf,
only: esmf_stateitem_flag, esmf_stateitem_notfound
14 use esmf,
only: esmf_geomtype_flag, esmf_geomtype_grid, esmf_geomtype_mesh
15 use esmf,
only: esmf_rc_val_outofrange, esmf_index_delocal, esmf_meshloc_element
16 use esmf,
only: esmf_typekind_r8
17 use esmf,
only:
operator(/=),
operator(==)
22 use mpp_domains_mod,
only: mpp_get_compute_domain
25 implicit none;
private
50 type(esmf_geomtype_flag),
intent(in) :: geomtype_in
60 subroutine mom_import(ocean_public, ocean_grid, importState, ice_ocean_boundary, rc)
63 type(esmf_state) ,
intent(inout) :: importstate
65 integer ,
intent(inout) :: rc
68 integer :: i, j, ig, jg, n
69 integer :: isc, iec, jsc, jec
70 character(len=128) :: fldname
71 real(esmf_kind_r8),
allocatable :: taux(:,:)
72 real(esmf_kind_r8),
allocatable :: tauy(:,:)
73 character(len=*) ,
parameter :: subname =
'(mom_import)'
82 call mpp_get_compute_domain(ocean_public%domain, isc, iec, jsc, jec)
88 isc, iec, jsc, jec, ice_ocean_boundary%p, rc=rc)
89 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
98 isc, iec, jsc, jec, ice_ocean_boundary%sw_flux_nir_dir, rc=rc)
99 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
108 isc, iec, jsc, jec, ice_ocean_boundary%sw_flux_nir_dif, rc=rc)
109 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
118 isc, iec, jsc, jec, ice_ocean_boundary%sw_flux_vis_dir, rc=rc)
119 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
128 isc, iec, jsc, jec, ice_ocean_boundary%sw_flux_vis_dif, rc=rc)
129 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
138 isc, iec, jsc, jec, ice_ocean_boundary%lw_flux, rc=rc)
139 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
147 allocate (taux(isc:iec,jsc:jec))
148 allocate (tauy(isc:iec,jsc:jec))
150 call state_getimport(importstate,
'mean_zonal_moment_flx', isc, iec, jsc, jec, taux, rc=rc)
151 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
155 call state_getimport(importstate,
'mean_merid_moment_flx', isc, iec, jsc, jec, tauy, rc=rc)
156 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
164 jg = j + ocean_grid%jsc - jsc
166 ig = i + ocean_grid%isc - isc
167 ice_ocean_boundary%u_flux(i,j) = ocean_grid%cos_rot(ig,jg)*taux(i,j) &
168 - ocean_grid%sin_rot(ig,jg)*tauy(i,j)
169 ice_ocean_boundary%v_flux(i,j) = ocean_grid%cos_rot(ig,jg)*tauy(i,j) &
170 + ocean_grid%sin_rot(ig,jg)*taux(i,j)
174 deallocate(taux, tauy)
180 isc, iec, jsc, jec, ice_ocean_boundary%t_flux, rc=rc)
181 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
190 isc, iec, jsc, jec, ice_ocean_boundary%q_flux, rc=rc)
191 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
200 isc, iec, jsc, jec, ice_ocean_boundary%lprec, rc=rc)
201 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
210 isc, iec, jsc, jec, ice_ocean_boundary%fprec, rc=rc)
211 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
223 ice_ocean_boundary%lrunoff (:,:) = 0._esmf_kind_r8
225 isc, iec, jsc, jec, ice_ocean_boundary%lrunoff,rc=rc)
226 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
232 ice_ocean_boundary%frunoff (:,:) = 0._esmf_kind_r8
234 isc, iec, jsc, jec, ice_ocean_boundary%frunoff,rc=rc)
235 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
241 ice_ocean_boundary%lrunoff_hflx(:,:) = 0._esmf_kind_r8
243 isc, iec, jsc, jec, ice_ocean_boundary%lrunoff_hflx, rc=rc)
244 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
250 ice_ocean_boundary%frunoff_hflx(:,:) = 0._esmf_kind_r8
252 isc, iec, jsc, jec, ice_ocean_boundary%frunoff_hflx, rc=rc)
253 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
261 ice_ocean_boundary%salt_flux(:,:) = 0._esmf_kind_r8
263 isc, iec, jsc, jec, ice_ocean_boundary%salt_flux,rc=rc)
264 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
272 ice_ocean_boundary%seaice_melt_heat(:,:) = 0._esmf_kind_r8
274 isc, iec, jsc, jec, ice_ocean_boundary%seaice_melt_heat,rc=rc)
275 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
283 ice_ocean_boundary%seaice_melt(:,:) = 0._esmf_kind_r8
285 isc, iec, jsc, jec, ice_ocean_boundary%seaice_melt,rc=rc)
286 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
297 ice_ocean_boundary%mi(:,:) = 0._esmf_kind_r8
299 isc, iec, jsc, jec, ice_ocean_boundary%mi, rc=rc)
300 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
308 subroutine mom_export(ocean_public, ocean_grid, ocean_state, exportState, clock, rc)
312 type(esmf_state) ,
intent(inout) :: exportstate
313 type(esmf_clock) ,
intent(in) :: clock
314 integer ,
intent(inout) :: rc
317 integer :: i, j, ig, jg
318 integer :: isc, iec, jsc, jec
319 integer :: iloc, jloc
320 integer :: iglob, jglob
323 real :: slp_l, slp_r, slp_c
324 real :: slope, u_min, u_max
326 type(esmf_timeinterval) :: timestep
329 type(esmf_stateitem_flag) :: itemflag
330 real(esmf_kind_r8),
allocatable :: omask(:,:)
331 real(esmf_kind_r8),
allocatable :: melt_potential(:,:)
332 real(esmf_kind_r8),
allocatable :: ocz(:,:), ocm(:,:)
333 real(esmf_kind_r8),
allocatable :: ocz_rot(:,:), ocm_rot(:,:)
334 real(esmf_kind_r8),
allocatable :: ssh(:,:)
335 real(esmf_kind_r8),
allocatable :: dhdx(:,:), dhdy(:,:)
336 real(esmf_kind_r8),
allocatable :: dhdx_rot(:,:), dhdy_rot(:,:)
337 character(len=*) ,
parameter :: subname =
'(mom_export)'
341 call esmf_clockget( clock, timestep=timestep, rc=rc)
342 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
347 call esmf_timeintervalget( timestep, s=dt_int, rc=rc )
348 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
354 if (real(dt_int) > 0.0)
then
355 inv_dt_int = 1.0 / real(dt_int)
364 call mpp_get_compute_domain(ocean_public%domain, isc, iec, jsc, jec)
370 allocate(omask(isc:iec, jsc:jec))
372 jg = j + ocean_grid%jsc - jsc
374 ig = i + ocean_grid%isc - isc
375 omask(i,j) = nint(ocean_grid%mask2dT(ig,jg))
380 isc, iec, jsc, jec, omask, ocean_grid, rc=rc)
381 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
392 isc, iec, jsc, jec, ocean_public%t_surf, ocean_grid, rc=rc)
393 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
402 isc, iec, jsc, jec, ocean_public%s_surf, ocean_grid, rc=rc)
403 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
415 allocate(ocz(isc:iec, jsc:jec))
416 allocate(ocm(isc:iec, jsc:jec))
417 allocate(ocz_rot(isc:iec, jsc:jec))
418 allocate(ocm_rot(isc:iec, jsc:jec))
421 jg = j + ocean_grid%jsc - jsc
423 ig = i + ocean_grid%isc - isc
424 ocz(i,j) = ocean_public%u_surf(i,j)
425 ocm(i,j) = ocean_public%v_surf(i,j)
426 ocz_rot(i,j) = ocean_grid%cos_rot(ig,jg)*ocz(i,j) + ocean_grid%sin_rot(ig,jg)*ocm(i,j)
427 ocm_rot(i,j) = ocean_grid%cos_rot(ig,jg)*ocm(i,j) - ocean_grid%sin_rot(ig,jg)*ocz(i,j)
432 isc, iec, jsc, jec, ocz_rot, ocean_grid, rc=rc)
433 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
439 isc, iec, jsc, jec, ocm_rot, ocean_grid, rc=rc)
440 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
445 deallocate(ocz, ocm, ocz_rot, ocm_rot)
450 call esmf_stateget(exportstate,
'So_bldepth', itemflag, rc=rc)
451 if (itemflag /= esmf_stateitem_notfound)
then
453 isc, iec, jsc, jec, ocean_public%obld, ocean_grid, rc=rc)
454 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
466 allocate(melt_potential(isc:iec, jsc:jec))
470 if (ocean_public%frazil(i,j) > 0.0)
then
471 melt_potential(i,j) = ocean_public%frazil(i,j) * inv_dt_int
473 melt_potential(i,j) = -ocean_public%melt_potential(i,j) * inv_dt_int
474 if (melt_potential(i,j) > 0.0) melt_potential(i,j) = 0.0
480 isc, iec, jsc, jec, melt_potential, ocean_grid, rc=rc)
481 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
486 deallocate(melt_potential)
491 call esmf_stateget(exportstate,
'sea_level', itemflag, rc=rc)
492 if (itemflag /= esmf_stateitem_notfound)
then
494 isc, iec, jsc, jec, ocean_public%sea_lev, ocean_grid, rc=rc)
495 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
505 allocate(ssh(ocean_grid%isd:ocean_grid%ied,ocean_grid%jsd:ocean_grid%jed))
506 allocate(dhdx(isc:iec, jsc:jec))
507 allocate(dhdy(isc:iec, jsc:jec))
508 allocate(dhdx_rot(isc:iec, jsc:jec))
509 allocate(dhdy_rot(isc:iec, jsc:jec))
511 ssh = 0.0_esmf_kind_r8
512 dhdx = 0.0_esmf_kind_r8
513 dhdy = 0.0_esmf_kind_r8
516 do j = ocean_grid%jsc, ocean_grid%jec
517 jloc = j + ocean_grid%jdg_offset
518 do i = ocean_grid%isc,ocean_grid%iec
519 iloc = i + ocean_grid%idg_offset
520 ssh(i,j) = ocean_public%sea_lev(iloc,jloc)
525 call pass_var(ssh, ocean_grid%domain)
532 j = jglob + ocean_grid%jsc - jsc
534 i = iglob + ocean_grid%isc - isc
536 slp_l = (ssh(i,j) - ssh(i-1,j)) * ocean_grid%mask2dCu(i-1,j)
537 if (ocean_grid%mask2dCu(i-1,j)==0.) slp_l = 0.
538 slp_r = (ssh(i+1,j) - ssh(i,j)) * ocean_grid%mask2dCu(i,j)
539 if (ocean_grid%mask2dCu(i+1,j)==0.) slp_r = 0.
540 slp_c = 0.5 * (slp_l + slp_r)
541 if ( (slp_l * slp_r) > 0.0 )
then
544 u_min = min( ssh(i-1,j), ssh(i,j), ssh(i+1,j) )
545 u_max = max( ssh(i-1,j), ssh(i,j), ssh(i+1,j) )
546 slope = sign( min( abs(slp_c), 2.*min( ssh(i,j) - u_min, u_max - ssh(i,j) ) ), slp_c )
552 dhdx(iglob,jglob) = slope * ocean_grid%US%m_to_L*ocean_grid%IdxT(i,j) * ocean_grid%mask2dT(i,j)
553 if (ocean_grid%mask2dT(i,j)==0.) dhdx(iglob,jglob) = 0.0
562 j = jglob + ocean_grid%jsc - jsc
564 i = iglob + ocean_grid%isc - isc
566 slp_l = ssh(i,j) - ssh(i,j-1) * ocean_grid%mask2dCv(i,j-1)
567 if (ocean_grid%mask2dCv(i,j-1)==0.) slp_l = 0.
568 slp_r = ssh(i,j+1) - ssh(i,j) * ocean_grid%mask2dCv(i,j)
569 if (ocean_grid%mask2dCv(i,j+1)==0.) slp_r = 0.
570 slp_c = 0.5 * (slp_l + slp_r)
571 if ((slp_l * slp_r) > 0.0)
then
574 u_min = min( ssh(i,j-1), ssh(i,j), ssh(i,j+1) )
575 u_max = max( ssh(i,j-1), ssh(i,j), ssh(i,j+1) )
576 slope = sign( min( abs(slp_c), 2.*min( ssh(i,j) - u_min, u_max - ssh(i,j) ) ), slp_c )
582 dhdy(iglob,jglob) = slope * ocean_grid%US%m_to_L*ocean_grid%IdyT(i,j) * ocean_grid%mask2dT(i,j)
583 if (ocean_grid%mask2dT(i,j)==0.) dhdy(iglob,jglob) = 0.0
591 jg = j + ocean_grid%jsc - jsc
593 ig = i + ocean_grid%isc - isc
594 dhdx_rot(i,j) = ocean_grid%cos_rot(ig,jg)*dhdx(i,j) + ocean_grid%sin_rot(ig,jg)*dhdy(i,j)
595 dhdy_rot(i,j) = ocean_grid%cos_rot(ig,jg)*dhdy(i,j) - ocean_grid%sin_rot(ig,jg)*dhdx(i,j)
600 isc, iec, jsc, jec, dhdx_rot, ocean_grid, rc=rc)
601 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
607 isc, iec, jsc, jec, dhdy_rot, ocean_grid, rc=rc)
608 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
613 deallocate(ssh, dhdx, dhdy, dhdx_rot, dhdy_rot)
619 type(esmf_state) ,
intent(in) :: State
620 character(len=*) ,
intent(in) :: fldname
621 real(ESMF_KIND_R8),
pointer ,
intent(in) :: fldptr(:)
622 integer,
optional ,
intent(out) :: rc
625 type(esmf_field) :: lfield
627 character(len=*),
parameter :: subname=
'(MOM_cap:State_GetFldPtr)'
629 call esmf_stateget(state, itemname=trim(fldname), field=lfield, rc=lrc)
630 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
634 call esmf_fieldget(lfield, farrayptr=fldptr, rc=lrc)
635 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
640 if (
present(rc)) rc = lrc
646 type(esmf_state) ,
intent(in) :: State
647 character(len=*) ,
intent(in) :: fldname
648 real(ESMF_KIND_R8),
pointer ,
intent(in) :: fldptr(:,:)
649 integer,
optional ,
intent(out) :: rc
652 type(esmf_field) :: lfield
654 character(len=*),
parameter :: subname=
'(MOM_cap:State_GetFldPtr)'
656 call esmf_stateget(state, itemname=trim(fldname), field=lfield, rc=lrc)
657 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
661 call esmf_fieldget(lfield, farrayptr=fldptr, rc=lrc)
662 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
667 if (
present(rc)) rc = lrc
672 subroutine state_getimport(state, fldname, isc, iec, jsc, jec, output, do_sum, rc)
673 type(esmf_state) ,
intent(in) :: state
674 character(len=*) ,
intent(in) :: fldname
675 integer ,
intent(in) :: isc
677 integer ,
intent(in) :: iec
679 integer ,
intent(in) :: jsc
681 integer ,
intent(in) :: jec
683 real (esmf_kind_r8) ,
intent(inout) :: output(isc:iec,jsc:jec)
684 logical,
optional ,
intent(in) :: do_sum
685 integer ,
intent(out) :: rc
688 type(esmf_stateitem_flag) :: itemflag
689 integer :: n, i, j, i1, j1
690 integer :: lbnd1,lbnd2
691 real(esmf_kind_r8),
pointer :: dataptr1d(:)
692 real(esmf_kind_r8),
pointer :: dataptr2d(:,:)
693 character(len=*) ,
parameter :: subname=
'(MOM_cap_methods:state_getimport)'
698 call esmf_stateget(state, trim(fldname), itemflag, rc=rc)
699 if (itemflag /= esmf_stateitem_notfound)
then
701 if (
geomtype == esmf_geomtype_mesh)
then
705 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
715 if (
present(do_sum))
then
716 output(i,j) = output(i,j) + dataptr1d(n)
718 output(i,j) = dataptr1d(n)
723 else if (
geomtype == esmf_geomtype_grid)
then
726 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
731 lbnd1 = lbound(dataptr2d,1)
732 lbnd2 = lbound(dataptr2d,2)
738 if (
present(do_sum))
then
739 output(i,j) = output(i,j) + dataptr2d(i1,j1)
741 output(i,j) = dataptr2d(i1,j1)
753 subroutine state_setexport(state, fldname, isc, iec, jsc, jec, input, ocean_grid, rc)
754 type(esmf_state) ,
intent(inout) :: state
755 character(len=*) ,
intent(in) :: fldname
756 integer ,
intent(in) :: isc
758 integer ,
intent(in) :: iec
760 integer ,
intent(in) :: jsc
762 integer ,
intent(in) :: jec
764 real (esmf_kind_r8) ,
intent(in) :: input(isc:iec,jsc:jec)
766 integer ,
intent(out) :: rc
769 type(esmf_stateitem_flag) :: itemflag
770 integer :: n, i, j, i1, j1, ig,jg
771 integer :: lbnd1,lbnd2
772 real(esmf_kind_r8),
pointer :: dataptr1d(:)
773 real(esmf_kind_r8),
pointer :: dataptr2d(:,:)
774 character(len=*) ,
parameter :: subname=
'(MOM_cap_methods:state_setexport)'
783 call esmf_stateget(state, trim(fldname), itemflag, rc=rc)
784 if (itemflag /= esmf_stateitem_notfound)
then
786 if (
geomtype == esmf_geomtype_mesh)
then
789 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
796 jg = j + ocean_grid%jsc - jsc
798 ig = i + ocean_grid%isc - isc
800 dataptr1d(n) = input(i,j) * ocean_grid%mask2dT(ig,jg)
804 else if (
geomtype == esmf_geomtype_grid)
then
807 if (esmf_logfounderror(rctocheck=rc, msg=esmf_logerr_passthru, &
812 lbnd1 = lbound(dataptr2d,1)
813 lbnd2 = lbound(dataptr2d,2)
817 jg = j + ocean_grid%jsc - jsc
820 ig = i + ocean_grid%isc - isc
821 dataptr2d(i1,j1) = input(i,j) * ocean_grid%mask2dT(ig,jg)