From 636e6000e4dbf9d4b2bdeca7216e700187ebcd30 Mon Sep 17 00:00:00 2001 From: Jian Sun Date: Fri, 12 Jun 2026 13:38:54 -0600 Subject: [PATCH 1/4] update map file option --- mediator/esmFldsExchange_cesm_mod.F90 | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/mediator/esmFldsExchange_cesm_mod.F90 b/mediator/esmFldsExchange_cesm_mod.F90 index 97ff04d5..979e6620 100644 --- a/mediator/esmFldsExchange_cesm_mod.F90 +++ b/mediator/esmFldsExchange_cesm_mod.F90 @@ -3320,7 +3320,7 @@ subroutine esmFldsExchange_cesm(gcomp, phase, rc) else if ( fldchk(is_local%wrap%FBImp(complnd, complnd), 'Flrl_rofsur'//trim(suffix), rc=rc) .and. & fldchk(is_local%wrap%FBExp(comprof) , 'Flrl_rofsur'//trim(suffix), rc=rc)) then - call addmap_from(complnd, 'Flrl_rofsur'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, 'unset') + call addmap_from(complnd, 'Flrl_rofsur'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, lnd2rof_map) call addmrg_to(comprof, 'Flrl_rofsur'//trim(suffix), & mrg_from=complnd, mrg_fld='Flrl_rofsur'//trim(suffix), & mrg_type='copy_with_weights', mrg_fracname=mrg_fracname_lnd2rof) @@ -3341,7 +3341,7 @@ subroutine esmFldsExchange_cesm(gcomp, phase, rc) else if ( fldchk(is_local%wrap%FBImp(complnd, complnd), 'Flrl_rofi'//trim(suffix), rc=rc) .and. & fldchk(is_local%wrap%FBExp(comprof) , 'Flrl_rofi'//trim(suffix), rc=rc)) then - call addmap_from(complnd, 'Flrl_rofi'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, 'unset') + call addmap_from(complnd, 'Flrl_rofi'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, lnd2rof_map) call addmrg_to(comprof, 'Flrl_rofi'//trim(suffix), & mrg_from=complnd, mrg_fld='Flrl_rofi'//trim(suffix), & mrg_type='copy_with_weights', mrg_fracname=mrg_fracname_lnd2rof) @@ -3362,7 +3362,7 @@ subroutine esmFldsExchange_cesm(gcomp, phase, rc) else if ( fldchk(is_local%wrap%FBImp(complnd, complnd), 'Flrl_rofgwl'//trim(suffix), rc=rc) .and. & fldchk(is_local%wrap%FBExp(comprof) , 'Flrl_rofgwl'//trim(suffix), rc=rc)) then - call addmap_from(complnd, 'Flrl_rofgwl'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, 'unset') + call addmap_from(complnd, 'Flrl_rofgwl'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, lnd2rof_map) call addmrg_to(comprof, 'Flrl_rofgwl'//trim(suffix), & mrg_from=complnd, mrg_fld='Flrl_rofgwl'//trim(suffix), & mrg_type='copy_with_weights', mrg_fracname=mrg_fracname_lnd2rof) @@ -3383,7 +3383,7 @@ subroutine esmFldsExchange_cesm(gcomp, phase, rc) else if ( fldchk(is_local%wrap%FBImp(complnd, complnd), 'Flrl_rofsub'//trim(suffix), rc=rc) .and. & fldchk(is_local%wrap%FBExp(comprof) , 'Flrl_rofsub'//trim(suffix), rc=rc)) then - call addmap_from(complnd, 'Flrl_rofsub'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, 'unset') + call addmap_from(complnd, 'Flrl_rofsub'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, lnd2rof_map) call addmrg_to(comprof, 'Flrl_rofsub'//trim(suffix), & mrg_from=complnd, mrg_fld='Flrl_rofsub'//trim(suffix), & mrg_type='copy_with_weights', mrg_fracname=mrg_fracname_lnd2rof) @@ -3404,7 +3404,7 @@ subroutine esmFldsExchange_cesm(gcomp, phase, rc) else if ( fldchk(is_local%wrap%FBImp(complnd, complnd), 'Flrl_irrig'//trim(suffix), rc=rc) .and. & fldchk(is_local%wrap%FBExp(comprof) , 'Flrl_irrig'//trim(suffix), rc=rc)) then - call addmap_from(complnd, 'Flrl_irrig'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, 'unset') + call addmap_from(complnd, 'Flrl_irrig'//trim(suffix), comprof, mapconsf, map_fracname_lnd2rof, lnd2rof_map) call addmrg_to(comprof, 'Flrl_irrig'//trim(suffix), & mrg_from=complnd, mrg_fld='Flrl_irrig'//trim(suffix), & mrg_type='copy_with_weights', mrg_fracname=mrg_fracname_lnd2rof) From 3d6dde4c3587a9b855b05e0da3f2d6d9f21a99cd Mon Sep 17 00:00:00 2001 From: Jian Sun Date: Fri, 12 Jun 2026 22:31:50 -0600 Subject: [PATCH 2/4] add option to provide lnd2rof_map consd file --- cime_config/config_component.xml | 9 +++++++ cime_config/namelist_definition_drv.xml | 10 ++++++++ mediator/med_fraction_mod.F90 | 34 ++++++++++++++++++++++--- mediator/med_map_mod.F90 | 10 ++++++-- 4 files changed, 57 insertions(+), 6 deletions(-) diff --git a/cime_config/config_component.xml b/cime_config/config_component.xml index 62611025..a536d47e 100644 --- a/cime_config/config_component.xml +++ b/cime_config/config_component.xml @@ -1423,6 +1423,15 @@ rof2lnd flux mapping file + + char + unset + run_domain + env_run.xml + lnd2rof conservative (destarea, 'consd') fraction mapping file used by the mediator + fraction init; 'unset' computes the weights online (memory-heavy at high resolution) + + char idmap diff --git a/cime_config/namelist_definition_drv.xml b/cime_config/namelist_definition_drv.xml index 7493bbdf..37c03bd8 100644 --- a/cime_config/namelist_definition_drv.xml +++ b/cime_config/namelist_definition_drv.xml @@ -2275,6 +2275,16 @@ idmap + + char + mapping + MED_attributes + lnd to rof conservative destarea ('consd') fraction mapping file read by the mediator + fraction init (med_fraction_mod); 'unset' computes the weights online + + $LND2ROF_FRAC_FMAPNAME + + char mapping diff --git a/mediator/med_fraction_mod.F90 b/mediator/med_fraction_mod.F90 index 9d58a43d..df87e9c7 100644 --- a/mediator/med_fraction_mod.F90 +++ b/mediator/med_fraction_mod.F90 @@ -181,6 +181,7 @@ subroutine med_fraction_init(gcomp, rc) use med_internalstate_mod , only : InternalState use med_map_mod , only : med_map_routehandles_init, med_map_rh_is_created use med_methods_mod , only : State_getNumFields => med_methods_State_getNumFields + use NUOPC , only : NUOPC_CompAttributeGet use perf_mod , only : t_startf, t_stopf ! input/output variables @@ -208,6 +209,8 @@ subroutine med_fraction_init(gcomp, rc) integer :: n,n1,ns integer :: maptype integer :: fieldCount + logical :: isPresent, isSet, lexist ! lnd2rof_fmap attribute presence / weight-file check + character(len=CX) :: lnd2rof_fmap ! consd (destarea) lnd->rof fraction-map file ($LND2ROF_FRAC_FMAPNAME) logical, save :: first_call = .true. character(len=*),parameter :: subname=' (med_fraction_init)' !--------------------------------------- @@ -584,10 +587,33 @@ subroutine med_fraction_init(gcomp, rc) if (is_local%wrap%comp_present(complnd)) then maptype = mapconsd if (.not. med_map_RH_is_created(is_local%wrap%RH(complnd,comprof,:),maptype, rc=rc)) then - call med_map_routehandles_init( complnd, comprof, & - FBSrc=is_local%wrap%FBImp(complnd,complnd), & - FBDst=is_local%wrap%FBImp(complnd,comprof), & - mapindex=maptype, RouteHandle=is_local%wrap%RH, rc=rc) + ! At ne1024pg2 resolution: the lnd->rof fraction map is the only grid-crossing + ! conservative coupling map; building it online (ESMF_FieldRegridStore -> + ! GeomRendezvous -> Zoltan_RCB) OOM-kills the job during DataInitialize. + ! Read offline consd (conserve/destarea) fraction weights from the file named by the + ! 'lnd2rof_fmap' attribute (xmlchange LND2ROF_FRAC_FMAPNAME=) when it is set + ! and present; otherwise fall back to the online path (no behavior change). + lnd2rof_fmap = 'unset' + call NUOPC_CompAttributeGet(gcomp, name='lnd2rof_fmap', value=lnd2rof_fmap, & + isPresent=isPresent, isSet=isSet, rc=rc) + if (ChkErr(rc,__LINE__,u_FILE_u)) return + if (.not. (isPresent .and. isSet)) lnd2rof_fmap = 'unset' + if (trim(lnd2rof_fmap) /= 'unset') then + inquire(file=trim(lnd2rof_fmap), exist=lexist) + if (.not. lexist) lnd2rof_fmap = 'unset' + end if + if (trim(lnd2rof_fmap) /= 'unset') then + call med_map_routehandles_init( complnd, comprof, & + FBSrc=is_local%wrap%FBImp(complnd,complnd), & + FBDst=is_local%wrap%FBImp(complnd,comprof), & + mapindex=maptype, RouteHandle=is_local%wrap%RH, & + mapfile=trim(lnd2rof_fmap), rc=rc) + else + call med_map_routehandles_init( complnd, comprof, & + FBSrc=is_local%wrap%FBImp(complnd,complnd), & + FBDst=is_local%wrap%FBImp(complnd,comprof), & + mapindex=maptype, RouteHandle=is_local%wrap%RH, rc=rc) + end if if (ChkErr(rc,__LINE__,u_FILE_u)) return end if diff --git a/mediator/med_map_mod.F90 b/mediator/med_map_mod.F90 index 9822dec1..a11f69d8 100644 --- a/mediator/med_map_mod.F90 +++ b/mediator/med_map_mod.F90 @@ -296,7 +296,7 @@ subroutine med_map_RouteHandles_initfrom_esmflds(gcomp, flds_scalar_name, llogun end subroutine med_map_RouteHandles_initfrom_esmflds !================================================================================ - subroutine med_map_routehandles_initfrom_fieldbundle(n1, n2, FBsrc, FBdst, mapindex, RouteHandle, rc) + subroutine med_map_routehandles_initfrom_fieldbundle(n1, n2, FBsrc, FBdst, mapindex, RouteHandle, mapfile, rc) use ESMF , only : ESMF_LogWrite, ESMF_LOGMSG_INFO, ESMF_SUCCESS, ESMF_LogFlush use ESMF , only : ESMF_Field, ESMF_FieldBundle, ESMF_RouteHandle @@ -313,6 +313,7 @@ subroutine med_map_routehandles_initfrom_fieldbundle(n1, n2, FBsrc, FBdst, mapin type(ESMF_FieldBundle) , intent(in) :: fBdst integer , intent(in) :: mapindex type(ESMF_RouteHandle) , intent(inout) :: RouteHandle(:,:,:) + character(len=*), optional, intent(in) :: mapfile ! read offline weights (ESMF_FieldSMMStore) instead of online regrid integer , intent(out) :: rc ! local variables @@ -333,7 +334,12 @@ subroutine med_map_routehandles_initfrom_fieldbundle(n1, n2, FBsrc, FBdst, mapin call med_methods_FB_getFieldN(FBDst, 1, flddst, rc) if (chkerr(rc,__LINE__,u_FILE_u)) return - call med_map_routehandles_initfrom_field(n1, n2, fldsrc, flddst, mapindex, routehandle(n1,n2,:), rc=rc) + if (present(mapfile)) then + call med_map_routehandles_initfrom_field(n1, n2, fldsrc, flddst, mapindex, routehandle(n1,n2,:), & + mapfile=mapfile, rc=rc) + else + call med_map_routehandles_initfrom_field(n1, n2, fldsrc, flddst, mapindex, routehandle(n1,n2,:), rc=rc) + end if if (chkerr(rc,__LINE__,u_FILE_u)) return if (dbug_flag > 1) then From 3ef024076ba545df7903e8369e336c96ae50a92f Mon Sep 17 00:00:00 2001 From: Jian Sun Date: Fri, 19 Jun 2026 00:38:17 -0600 Subject: [PATCH 3/4] reuse ocean field existing mesh handle to avoid duplicate full esmf mesh --- mediator/med_phases_aofluxes_mod.F90 | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/mediator/med_phases_aofluxes_mod.F90 b/mediator/med_phases_aofluxes_mod.F90 index 103d37ba..453653c4 100644 --- a/mediator/med_phases_aofluxes_mod.F90 +++ b/mediator/med_phases_aofluxes_mod.F90 @@ -582,7 +582,10 @@ subroutine med_aofluxes_init_ogrid(gcomp, aoflux_in, aoflux_out, rc) if (chkerr(rc,__LINE__,u_FILE_u)) return call ESMF_FieldGet(lfield, mesh=lmesh, rc=rc) if (chkerr(rc,__LINE__,u_FILE_u)) return - is_local%wrap%aoflux_mesh = ESMF_MeshCreate(lmesh, rc=rc) + ! Reuse the ocean field's mesh directly rather than building a duplicate full + ! ESMF mesh (ne1024pg2) per rank. lmesh persists in FBArea(compocn) and + ! aoflux_mesh is never destroyed, so sharing the handle is safe (ogrid path). + is_local%wrap%aoflux_mesh = lmesh call ESMF_MeshGet(lmesh, coordSys=coordSys, rc=rc) if (chkerr(rc,__LINE__,u_FILE_u)) return if (coordSys /= ESMF_COORDSYS_CART) then From 9437041df6701ee3cc555bf4cc9117487c922b4a Mon Sep 17 00:00:00 2001 From: Jian Sun Date: Fri, 26 Jun 2026 14:14:34 -0600 Subject: [PATCH 4/4] address bill's comments --- cime_config/config_component.xml | 16 ++++++------- cime_config/namelist_definition_drv.xml | 3 ++- mediator/med_fraction_mod.F90 | 31 +++++++++++++------------ mediator/med_phases_aofluxes_mod.F90 | 5 ++-- 4 files changed, 29 insertions(+), 26 deletions(-) diff --git a/cime_config/config_component.xml b/cime_config/config_component.xml index a536d47e..f7cfc844 100644 --- a/cime_config/config_component.xml +++ b/cime_config/config_component.xml @@ -1412,24 +1412,24 @@ idmap run_domain env_run.xml - lnd2rof flux mapping file + lnd2rof flux mapping file (conservative, conserve/fraction 'consf' mapping) - + char - idmap + unset run_domain env_run.xml - rof2lnd flux mapping file + lnd2rof conservative (destarea, 'consd') fraction mapping file used by the mediator + fraction init; 'unset' computes the weights online (memory-heavy at high resolution) - + char - unset + idmap run_domain env_run.xml - lnd2rof conservative (destarea, 'consd') fraction mapping file used by the mediator - fraction init; 'unset' computes the weights online (memory-heavy at high resolution) + rof2lnd flux mapping file diff --git a/cime_config/namelist_definition_drv.xml b/cime_config/namelist_definition_drv.xml index 37c03bd8..808f61c0 100644 --- a/cime_config/namelist_definition_drv.xml +++ b/cime_config/namelist_definition_drv.xml @@ -2269,7 +2269,8 @@ mapping abs MED_attributes - lnd to rof mapping, 'unset' or 'idmap' are normal possible values (mapping file given for mizuRoute grids) + lnd to rof flux mapping (conservative, conserve/fraction 'consf' mapping); 'unset' or 'idmap' + are normal possible values (mapping file given for mizuRoute grids) $LND2ROF_FMAPNAME idmap diff --git a/mediator/med_fraction_mod.F90 b/mediator/med_fraction_mod.F90 index df87e9c7..805af1ed 100644 --- a/mediator/med_fraction_mod.F90 +++ b/mediator/med_fraction_mod.F90 @@ -169,7 +169,7 @@ subroutine med_fraction_init(gcomp, rc) ! Initialize FBFrac(:) field bundles use ESMF , only : ESMF_LogWrite, ESMF_LOGMSG_INFO - use ESMF , only : ESMF_SUCCESS + use ESMF , only : ESMF_SUCCESS, ESMF_FAILURE, ESMF_LogSetError use ESMF , only : ESMF_GridComp, ESMF_GridCompGet, ESMF_StateIsCreated use ESMF , only : ESMF_FieldBundle, ESMF_FieldBundleIsCreated, ESMF_FieldBundleDestroy use ESMF , only : ESMF_FieldBundleGet @@ -209,8 +209,8 @@ subroutine med_fraction_init(gcomp, rc) integer :: n,n1,ns integer :: maptype integer :: fieldCount - logical :: isPresent, isSet, lexist ! lnd2rof_fmap attribute presence / weight-file check - character(len=CX) :: lnd2rof_fmap ! consd (destarea) lnd->rof fraction-map file ($LND2ROF_FRAC_FMAPNAME) + logical :: isPresent, isSet, lexist + character(len=CX) :: lnd2rof_fmap ! consd (destarea) lnd->rof fraction-map file logical, save :: first_call = .true. character(len=*),parameter :: subname=' (med_fraction_init)' !--------------------------------------- @@ -587,22 +587,23 @@ subroutine med_fraction_init(gcomp, rc) if (is_local%wrap%comp_present(complnd)) then maptype = mapconsd if (.not. med_map_RH_is_created(is_local%wrap%RH(complnd,comprof,:),maptype, rc=rc)) then - ! At ne1024pg2 resolution: the lnd->rof fraction map is the only grid-crossing - ! conservative coupling map; building it online (ESMF_FieldRegridStore -> - ! GeomRendezvous -> Zoltan_RCB) OOM-kills the job during DataInitialize. - ! Read offline consd (conserve/destarea) fraction weights from the file named by the - ! 'lnd2rof_fmap' attribute (xmlchange LND2ROF_FRAC_FMAPNAME=) when it is set - ! and present; otherwise fall back to the online path (no behavior change). - lnd2rof_fmap = 'unset' + ! The lnd->rof fraction map may be the only grid-crossing conservative coupling + ! map in a configuration, and computing its weights online (ESMF_FieldRegridStore) + ! can be prohibitively memory-heavy at high resolution. If the 'lnd2rof_fmap' + ! attribute names a file of offline consd (conserve/destarea) fraction weights, + ! read the weights from that file; otherwise compute them online. call NUOPC_CompAttributeGet(gcomp, name='lnd2rof_fmap', value=lnd2rof_fmap, & isPresent=isPresent, isSet=isSet, rc=rc) if (ChkErr(rc,__LINE__,u_FILE_u)) return if (.not. (isPresent .and. isSet)) lnd2rof_fmap = 'unset' - if (trim(lnd2rof_fmap) /= 'unset') then - inquire(file=trim(lnd2rof_fmap), exist=lexist) - if (.not. lexist) lnd2rof_fmap = 'unset' - end if - if (trim(lnd2rof_fmap) /= 'unset') then + if (lnd2rof_fmap /= 'unset') then + inquire(file=lnd2rof_fmap, exist=lexist) + if (.not. lexist) then + call ESMF_LogSetError(ESMF_FAILURE, & + msg=trim(subname)//': lnd2rof_fmap weight file not found: '//trim(lnd2rof_fmap), & + line=__LINE__, file=u_FILE_u, rcToReturn=rc) + return + end if call med_map_routehandles_init( complnd, comprof, & FBSrc=is_local%wrap%FBImp(complnd,complnd), & FBDst=is_local%wrap%FBImp(complnd,comprof), & diff --git a/mediator/med_phases_aofluxes_mod.F90 b/mediator/med_phases_aofluxes_mod.F90 index 453653c4..89cdff07 100644 --- a/mediator/med_phases_aofluxes_mod.F90 +++ b/mediator/med_phases_aofluxes_mod.F90 @@ -583,8 +583,9 @@ subroutine med_aofluxes_init_ogrid(gcomp, aoflux_in, aoflux_out, rc) call ESMF_FieldGet(lfield, mesh=lmesh, rc=rc) if (chkerr(rc,__LINE__,u_FILE_u)) return ! Reuse the ocean field's mesh directly rather than building a duplicate full - ! ESMF mesh (ne1024pg2) per rank. lmesh persists in FBArea(compocn) and - ! aoflux_mesh is never destroyed, so sharing the handle is safe (ogrid path). + ! ESMF mesh per rank (a meaningful memory savings at high resolution). lmesh + ! persists in FBArea(compocn) and aoflux_mesh is never destroyed, so sharing + ! the handle is safe (ogrid path). is_local%wrap%aoflux_mesh = lmesh call ESMF_MeshGet(lmesh, coordSys=coordSys, rc=rc) if (chkerr(rc,__LINE__,u_FILE_u)) return