ESMF_MeshMatch Function

public function ESMF_MeshMatch(mesh1, mesh2, rc)

Arguments

Type IntentOptional Attributes Name
type(ESMF_Mesh), intent(in) :: mesh1
type(ESMF_Mesh), intent(in) :: mesh2
integer, intent(out), optional :: rc

Return Value logical


Calls

proc~~esmf_meshmatch~~CallsGraph proc~esmf_meshmatch ESMF_MeshMatch c_esmc_meshgetdimensions c_esmc_meshgetdimensions proc~esmf_meshmatch->c_esmc_meshgetdimensions c_esmc_meshgetelemdistgrid c_esmc_meshgetelemdistgrid proc~esmf_meshmatch->c_esmc_meshgetelemdistgrid c_esmc_meshgetnodedistgrid c_esmc_meshgetnodedistgrid proc~esmf_meshmatch->c_esmc_meshgetnodedistgrid c_esmc_meshgetownedelemcount c_esmc_meshgetownedelemcount proc~esmf_meshmatch->c_esmc_meshgetownedelemcount c_esmc_meshgetownednodecount c_esmc_meshgetownednodecount proc~esmf_meshmatch->c_esmc_meshgetownednodecount c_esmc_meshgetstatus c_esmc_meshgetstatus proc~esmf_meshmatch->c_esmc_meshgetstatus proc~esmf_distgridmatch ESMF_DistGridMatch proc~esmf_meshmatch->proc~esmf_distgridmatch proc~esmf_distgridsetinitcreated ESMF_DistGridSetInitCreated proc~esmf_meshmatch->proc~esmf_distgridsetinitcreated proc~esmf_imerr ESMF_IMErr proc~esmf_meshmatch->proc~esmf_imerr proc~esmf_logfoundallocerror ESMF_LogFoundAllocError proc~esmf_meshmatch->proc~esmf_logfoundallocerror proc~esmf_logfounderror ESMF_LogFoundError proc~esmf_meshmatch->proc~esmf_logfounderror proc~esmf_logseterror ESMF_LogSetError proc~esmf_meshmatch->proc~esmf_logseterror proc~esmf_meshgetelemarea ESMF_MeshGetElemArea proc~esmf_meshmatch->proc~esmf_meshgetelemarea proc~esmf_meshgetinit ESMF_MeshGetInit proc~esmf_meshmatch->proc~esmf_meshgetinit proc~esmf_distgridmatch->proc~esmf_imerr proc~esmf_distgridmatch->proc~esmf_logfounderror c_esmc_distgridmatch c_esmc_distgridmatch proc~esmf_distgridmatch->c_esmc_distgridmatch proc~esmf_distgridgetinit ESMF_DistGridGetInit proc~esmf_distgridmatch->proc~esmf_distgridgetinit proc~esmf_imerr->proc~esmf_logfounderror proc~esmf_initcheckdeep ESMF_InitCheckDeep proc~esmf_imerr->proc~esmf_initcheckdeep esmf_breakpoint esmf_breakpoint proc~esmf_logfoundallocerror->esmf_breakpoint proc~esmf_logrc2msg ESMF_LogRc2Msg proc~esmf_logfoundallocerror->proc~esmf_logrc2msg proc~esmf_logwrite ESMF_LogWrite proc~esmf_logfoundallocerror->proc~esmf_logwrite proc~esmf_logfounderror->esmf_breakpoint proc~esmf_logfounderror->proc~esmf_logrc2msg proc~esmf_logfounderror->proc~esmf_logwrite proc~esmf_logseterror->esmf_breakpoint proc~esmf_logseterror->proc~esmf_logrc2msg proc~esmf_logseterror->proc~esmf_logwrite proc~esmf_meshgetelemarea->c_esmc_meshgetstatus proc~esmf_meshgetelemarea->proc~esmf_imerr proc~esmf_meshgetelemarea->proc~esmf_logfounderror proc~esmf_meshgetelemarea->proc~esmf_logseterror proc~esmf_meshgetelemarea->proc~esmf_meshgetinit c_esmc_meshgetarea c_esmc_meshgetarea proc~esmf_meshgetelemarea->c_esmc_meshgetarea c_esmc_meshgetisfree c_esmc_meshgetisfree proc~esmf_meshgetelemarea->c_esmc_meshgetisfree c_esmc_loggeterrormsg c_esmc_loggeterrormsg proc~esmf_logrc2msg->c_esmc_loggeterrormsg c_esmc_vmwtime c_esmc_vmwtime proc~esmf_logwrite->c_esmc_vmwtime proc~esmf_logclose ESMF_LogClose proc~esmf_logwrite->proc~esmf_logclose proc~esmf_logflush ESMF_LogFlush proc~esmf_logwrite->proc~esmf_logflush proc~esmf_logopenfile ESMF_LogOpenFile proc~esmf_logwrite->proc~esmf_logopenfile proc~esmf_utiliounitflush ESMF_UtilIOUnitFlush proc~esmf_logwrite->proc~esmf_utiliounitflush proc~esmf_utilstring2array ESMF_UtilString2Array proc~esmf_logwrite->proc~esmf_utilstring2array proc~esmf_logclose->proc~esmf_logflush proc~esmf_logflush->proc~esmf_utiliounitflush proc~esmf_utilarray2string ESMF_UtilArray2String proc~esmf_logflush->proc~esmf_utilarray2string proc~esmf_logopenfile->proc~esmf_utiliounitflush proc~esmf_utiliounitget ESMF_UtilIOUnitGet proc~esmf_logopenfile->proc~esmf_utiliounitget

Called by

proc~~esmf_meshmatch~~CalledByGraph proc~esmf_meshmatch ESMF_MeshMatch proc~esmf_xgridgeombasematch ESMF_XGridGeomBaseMatch proc~esmf_xgridgeombasematch->proc~esmf_meshmatch proc~esmf_xgridmatch ESMF_XGridMatch proc~esmf_xgridmatch->proc~esmf_xgridgeombasematch proc~esmf_fieldregridstorex ESMF_FieldRegridStoreX proc~esmf_fieldregridstorex->proc~esmf_xgridmatch interface~esmf_fieldregridstore ESMF_FieldRegridStore interface~esmf_fieldregridstore->proc~esmf_fieldregridstorex

Source Code

  function ESMF_MeshMatch(mesh1, mesh2, rc)
!
! !RETURN VALUE:
    logical :: ESMF_MeshMatch

! !ARGUMENTS:
    type(ESMF_Mesh),  intent(in)             :: mesh1
    type(ESMF_Mesh),  intent(in)             :: mesh2
    integer,          intent(out),  optional :: rc
!
!
! !DESCRIPTION:
!      Check if {\tt mesh1} and {\tt mesh2} match. Returns
!      .true. if Mesh objects match, .false. otherwise. This
!      method current just checks if mesh1 and mesh2s distgrids match,
!      future work will do a more complex check.
!
!     The arguments are:
!     \begin{description}
!     \item[mesh1]
!          {\tt ESMF\_Mesh} object.
!     \item[mesh2]
!          {\tt ESMF\_Mesh} object.
!     \item[{[rc]}]
!          Return code; equals {\tt ESMF\_SUCCESS} if there are no errors.
!     \end{description}
!
!EOPI
!------------------------------------------------------------------------------
    integer :: i, localrc
    type(ESMF_MeshStatus_Flag) :: status1, status2
    integer :: mesh1sdim, mesh1pdim, mesh2sdim, mesh2pdim
    integer :: mesh1numNode, mesh1numElem, mesh2numNode, mesh2numElem
    type(ESMF_CoordSys_Flag) :: mesh1coordSys, mesh2coordSys
    type(ESMF_DistGridMatch_Flag) :: matchResultNode, matchResultElem
    type(ESMF_DistGrid)           :: nodeDistGrid1, nodeDistGrid2, &
                                     elemDistGrid1, elemDistGrid2

    real(ESMF_KIND_R8), pointer       :: area1(:), area2(:)
    real(ESMF_KIND_R8), allocatable   :: coord1(:), coord2(:)
    integer                           :: nOwnedNodes1, nOwnedElems1
    integer                           :: nOwnedNodes2, nOwnedElems2

    ! initialize return code; assume routine not implemented
    localrc = ESMF_RC_NOT_IMPL
    if (present(rc)) rc = ESMF_RC_NOT_IMPL

    ! init to one setting in case of error
    ESMF_MeshMatch = .false.

    ! Check init status of arguments
    ESMF_INIT_CHECK_DEEP(ESMF_MeshGetInit, mesh1, rc)
    ESMF_INIT_CHECK_DEEP(ESMF_MeshGetInit, mesh2, rc)

    ! If meshes have not been fully created
    call C_ESMC_MeshGetStatus(mesh1, status1)
    if (status1 .ne. ESMF_MESHSTATUS_COMPLETE) then
       call ESMF_LogSetError(rcToCheck=ESMF_RC_OBJ_WRONG, &
                 msg="- the mesh has not been fully created", &
                 ESMF_CONTEXT, rcToReturn=rc)
       return
    endif

    call C_ESMC_MeshGetStatus(mesh2, status2)
    if (status2 .ne. ESMF_MESHSTATUS_COMPLETE) then
       call ESMF_LogSetError(rcToCheck=ESMF_RC_OBJ_WRONG, &
                 msg="- the mesh has not been fully created", &
                 ESMF_CONTEXT, rcToReturn=rc)
       return
    endif

    call C_ESMC_MeshGetDimensions(mesh1, mesh1sdim, mesh1pdim, &
                                  mesh1coordSys, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    call C_ESMC_MeshGetDimensions(mesh2, mesh2sdim, mesh2pdim, &
                                  mesh2coordSys, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    call C_ESMC_MeshGetOwnedNodeCount(mesh1, mesh1numNode, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call C_ESMC_MeshGetOwnedElemCount(mesh1, mesh1numElem, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call C_ESMC_MeshGetOwnedNodeCount(mesh2, mesh2numNode, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call C_ESMC_MeshGetOwnedElemCount(mesh2, mesh2numElem, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call c_ESMC_MeshGetNodeDistGrid(mesh1, nodeDistGrid1, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    ! Set init code for deep C++ DistGrid object
    call ESMF_DistGridSetInitCreated(nodeDistGrid1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
    
    call c_ESMC_MeshGetNodeDistGrid(mesh2, nodeDistGrid2, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    ! Set init code for deep C++ DistGrid object
    call ESMF_DistGridSetInitCreated(nodeDistGrid2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
      
    call c_ESMC_MeshGetElemDistGrid(mesh1, elemDistGrid1, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    ! Set init code for deep C++ DistGrid object
    call ESMF_DistGridSetInitCreated(elemDistGrid1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
      
    call c_ESMC_MeshGetElemDistGrid(mesh2, elemDistGrid2, localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
        ESMF_CONTEXT, rcToReturn=rc)) return
    
    ! Set init code for deep C++ DistGrid object
    call ESMF_DistGridSetInitCreated(elemDistGrid2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    ! For now just make match to mean that the Mesh's have the same distgrids because that's
    ! all the fields care about
    matchResultNode=ESMF_DistGridMatch(nodeDistGrid1, nodeDistGrid2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    matchResultElem=ESMF_DistGridMatch(elemDistGrid1, elemDistGrid2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    ! return successfully
    if ((matchResultNode >= ESMF_DISTGRIDMATCH_EXACT) .and. &
      (matchResultElem >= ESMF_DISTGRIDMATCH_EXACT)) then
      ESMF_MeshMatch = .true.
    else
      ESMF_MeshMatch = .false.
      return
    endif

    ! check area
    allocate(area1(mesh1numElem), area2(mesh2numElem), stat=localrc)
    if (ESMF_LogFoundAllocError(localrc, &
        msg="- MeshMatch: Allocating area1 and area2 failed ", &
        ESMF_CONTEXT, rcToReturn=rc)) return
    call ESMF_MeshGetElemArea(mesh1, area1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
    call ESMF_MeshGetElemArea(mesh2, area2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    do i = 1, mesh1numElem
      if(area1(i) /= area2(i)) then
        ESMF_MeshMatch = .false.
        deallocate(area1, area2)
        return
      endif
    enddo
    deallocate(area1, area2)

#if 0
    ! check nodal coordinates
    if(mesh1sdim /= mesh2sdim) then
      ESMF_MeshMatch = .false.
      return
    endif
    if(mesh1numNode /= mesh2numNode) then
      ESMF_MeshMatch = .false.
      return
    endif
    call ESMF_MeshGet(mesh1, numOwnedNodes=nOwnedNodes1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
    call ESMF_MeshGet(mesh2, numOwnedNodes=nOwnedNodes2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return
    if(nOwnedNodes1 /= nOwnedNodes2) then
      ESMF_MeshMatch = .false.
      return
    endif
    allocate(coord1(nOwnedNodes1*mesh1sdim), &
             coord2(nOwnedNodes2*mesh2sdim), stat=localrc)
    if (ESMF_LogFoundAllocError(localrc, &
        msg="- MeshMatch: Allocating coord1 and coord2 failed ", &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call ESMF_MeshGet(mesh1, ownedNodeCoords=coord1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    call ESMF_MeshGet(mesh2, ownedNodeCoords=coord2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    do i = 1, nOwnedNodes1
      if(coord1(i) /= coord2(i)) then
        ESMF_MeshMatch = .false.
        deallocate(coord1, coord2)
        return
      endif
    enddo

    ! check element coordinates
    ! Currently mesh element coordinates are not required
    if(mesh1numElem /= mesh2numElem) then
      ESMF_MeshMatch = .false.
      return
    endif
    nCoord = mesh1numElem * mesh1sdim
    allocate(coord1(nCoord), coord2(mesh2numElem), stat=localrc)
    if (ESMF_LogFoundAllocError(localrc, &
        msg="- MeshMatch: Allocating coord1 and coord2 failed ", &
        ESMF_CONTEXT, rcToReturn=rc)) return

    call ESMF_MeshGet(mesh1, ownedElemCoords=coord1, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    call ESMF_MeshGet(mesh2, ownedElemCoords=coord2, rc=localrc)
    if (ESMF_LogFoundError(localrc, ESMF_ERR_PASSTHRU, &
      ESMF_CONTEXT, rcToReturn=rc)) return

    do i = 1, mesh1numElem
      if(coord1(i) /= coord2(i)) then
        ESMF_MeshMatch = .false.
        deallocate(coord1, coord2)
        return
      endif
    enddo
    deallocate(coord1, coord2)
#endif

    if (present(rc)) rc = ESMF_SUCCESS

  end function ESMF_MeshMatch