#include <misc.h>
#include <preproc.h>
#define BUILDPIO
#undef BUILDPIO
#undef SWITCH_DIMS
#define SWITCH_DIMS
module ncdio 24,37
!-----------------------------------------------------------------------
!BOP
!
! !MODULE: ncdioMod
!
! !DESCRIPTION:
! Generic interfaces to write fields to netcdf files
!
! !USES:
use shr_kind_mod
, only : r8 => shr_kind_r8
use spmdMod
, only : masterproc, mpicom, MPI_REAL8, MPI_INTEGER, &
MPI_LOGICAL
use clmtype
, only : gratm, grlnd, nameg, namel, namec, namep, allrof
use clm_varcon
, only : spval,ispval
use shr_sys_mod
, only : shr_sys_flush
use abortutils
, only : endrun
use clm_varctl
, only : single_column
use clm_varctl
, only : iulog
use clm_varctl
, only : ncd_lowmem2d, ncd_pio_def
use clm_varctl
, only : ncd_pio_UseRearranger, ncd_pio_useBoxRearr
use clm_varctl
, only : ncd_pio_SerialCDF, ncd_pio_IODOF_rootonly
use clm_varctl
, only : ncd_pio_DebugLevel, ncd_pio_num_iotasks
use clm_mct_mod
use spmdGathScatMod
use decompMod
, only : get_clmlevel_gsize,get_clmlevel_dsize
use perf_mod , only : t_startf, t_stopf
#if (defined BUILDPIO)
use piolib_mod ! _EXTERNAL
use pio_types ! _EXTERNAL
use pio_kinds , only : pio_offset
#endif
!
! !PUBLIC TYPES:
implicit none
include 'netcdf.inc'
save
!
! !PUBLIC MEMBER FUNCTIONS:
!
public :: check_ret ! checks return status of netcdf calls
#if (defined BUILDPIO)
public :: check_ret_pio ! checks return status of pio calls
#endif
public :: check_var ! determine if variable is on netcdf file
public :: check_dim ! validity check on dimension
public :: ncd_open ! open file
public :: ncd_close ! close file
public :: ncd_redef ! enter define mode
public :: ncd_enddef ! end define mode
public :: ncd_setfill ! set file value
public :: ncd_putatt ! put attribute
public :: ncd_defdim ! define dimension
public :: ncd_inqdid ! inquire dimension id
public :: ncd_inqdname ! inquire dimension name
public :: ncd_inqdlen ! inquire dimension length
public :: ncd_defvar ! define variables
public :: ncd_inqvid ! inquire variable id
public :: ncd_inqvname ! inquire variable name
public :: ncd_inqvdims ! inquire variable ndims
public :: ncd_inqvdids ! inquire variable dimids
public :: ncd_iolocal ! write local data
public :: ncd_ioglobal! write global data
integer,parameter,public :: ncd_int = nf_int
integer,parameter,public :: ncd_float = nf_float
integer,parameter,public :: ncd_double = nf_double
integer,parameter,public :: ncd_char = nf_char
integer,parameter,public :: ncd_global = nf_global
integer,parameter,public :: ncd_write = nf_write
integer,parameter,public :: ncd_nowrite = nf_nowrite
integer,parameter,public :: ncd_clobber = nf_clobber
integer,parameter,public :: ncd_noclobber = nf_noclobber
integer,parameter,public :: ncd_share = nf_share
integer,parameter,public :: ncd_fill = nf_fill
integer,parameter,public :: ncd_nofill = nf_nofill
integer,parameter,public :: ncd_unlimited = nf_unlimited
!
! !REVISION HISTORY:
!
!
! !PRIVATE MEMBER FUNCTIONS:
!
interface ncd_putatt 31
module procedure ncd_putatt_int
module procedure ncd_putatt_real
module procedure ncd_putatt_char
end interface
interface ncd_defvar 456
module procedure ncd_defvar_bynf
module procedure ncd_defvar_bygrid
end interface
interface ncd_iolocal 512
module procedure ncd_iolocal_int_1d
module procedure ncd_iolocal_real_1d
module procedure ncd_iolocal_int_2d
module procedure ncd_iolocal_real_2d
module procedure ncd_iolocal_gs_real1d
module procedure ncd_iolocal_gs_int1d
module procedure ncd_iolocal_gs_real2d
module procedure ncd_iolocal_gs_int2d
end interface
interface ncd_ioglobal 62
module procedure ncd_ioglobal_int_var
module procedure ncd_ioglobal_real_var
module procedure ncd_ioglobal_int_1d
module procedure ncd_ioglobal_real_1d
module procedure ncd_ioglobal_char_1d
module procedure ncd_ioglobal_int_2d
module procedure ncd_ioglobal_real_2d
module procedure ncd_ioglobal_int_3d
module procedure ncd_ioglobal_real_3d
end interface
private :: ncd_inqvdesc ! inquire variable descriptor
private :: ncd_inqiodesc ! inquire variable descriptor
#if (defined BUILDPIO)
private :: ncd_setDOF ! set DOF arrays for pio
#endif
private :: scam_field_offsets ! get offset to proper lat/lon gridcell for SCAM
logical,parameter,private :: lbcast_def = .false. ! lbcast default
integer,parameter,private :: debug = 0 ! local debug level
#if (defined BUILDPIO)
integer,private :: pio_num_iotasks
integer,private :: pio_num_aggregator
integer,private :: pio_io_rank
logical,private :: pio_IOproc
type(File_desc_t) :: pio_File
type pio_iodesc_plus_type
character(len=32) :: name
logical :: set
integer :: ndims
integer :: dimids(4)
integer :: type
type(IO_desc_t),pointer :: pio_ioDesc
end type pio_iodesc_plus_type
integer,parameter ,private :: pio_max_iodesc = 50
integer ,private :: pio_num_iodesc = 0
type(pio_iodesc_plus_type) ,private, target :: pio_iodesc_list(pio_max_iodesc)
type pio_vardesc_plus_type
character(len=64) :: name
integer :: iodnum ! iodesc associated with vardesc
type(Var_desc_t) :: pio_varDesc
end type pio_vardesc_plus_type
integer,parameter ,private :: pio_max_vardesc = 500
integer ,private :: pio_num_vardesc = 0
type(pio_vardesc_plus_type),private, target :: pio_varDesc_list(pio_max_vardesc)
#endif
!EOP
!-----------------------------------------------------------------------
contains
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: check_dim
!
! !INTERFACE:
subroutine check_dim(ncid, dimname, value, usepio) 28,4
!
! !DESCRIPTION:
! Validity check on dimension
!
! !ARGUMENTS:
implicit none
integer, intent(in) :: ncid
character(len=*), intent(in) :: dimname
integer, intent(in) :: value
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: dimid, dimlen ! temporaries
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='check_dim' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
if (masterproc) write(iulog,*) trim(subname),' WARNING: pio not implemented'
else
if (.not. masterproc) return
call check_ret
(nf_inq_dimid (ncid, trim(dimname), dimid), 'check_dim: dimname='//trim(dimname)//' ')
call check_ret
(nf_inq_dimlen (ncid, dimid, dimlen), 'check_dim')
if (dimlen /= value) then
write(iulog,*) trim(subname),' ERROR: mismatch of input dimension ',dimlen, &
' with expected value ',value,' for variable ',trim(dimname)
call endrun
()
end if
endif
end subroutine check_dim
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: check_var
!
! !INTERFACE:
subroutine check_var(ncid, varname, varid, readvar, usepio) 9,1
!
! !DESCRIPTION:
! Check if variable is on netcdf file
!
! !ARGUMENTS:
implicit none
integer, intent(in) :: ncid
character(len=*), intent(in) :: varname
integer, intent(out) :: varid
logical, intent(out) :: readvar
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: ret ! return value
logical :: lusepio ! local usepio variable
#if (defined BUILDPIO)
type(Var_desc_t) :: pio_varDesc
#endif
character(len=*),parameter :: subname='check_var' ! subroutine name
!-----------------------------------------------------------------------
varid = -1
readvar = .true.
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
ret = PIO_inq_varid (pio_File, varname, pio_varDesc)
if (ret/=PIO_noerr) then
if (masterproc) write(iulog,*) trim(subname),': variable ',trim(varname),' is not on dataset'
readvar = .false.
end if
#endif
else
if (.not. masterproc) return
ret = nf_inq_varid (ncid, varname, varid)
if (ret/=NF_NOERR) then
write(iulog,*) trim(subname),': variable ',trim(varname),' is not on dataset'
readvar = .false.
end if
endif
end subroutine check_var
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: check_ret
!
! !INTERFACE:
subroutine check_ret(ret, cstring) 316,2
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer, intent(in) :: ret
character(len=*) :: cstring
!
! !REVISION HISTORY:
!
!EOP
character(len=*),parameter :: subname='check_ret' ! subroutine name
!-----------------------------------------------------------------------
if (ret /= NF_NOERR) then
write(iulog,*)'netcdf error from ',trim(subname),':',trim(cstring),':',trim(NF_STRERROR(ret))
call endrun
()
end if
end subroutine check_ret
#if (defined BUILDPIO)
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: check_ret_pio
!
! !INTERFACE:
subroutine check_ret_pio(ret, cstring) 26,1
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer, intent(in) :: ret
character(len=*) :: cstring
!
! !REVISION HISTORY:
!
!EOP
character(len=*),parameter :: subname='check_ret_pio' ! subroutine name
!-----------------------------------------------------------------------
if (ret /= PIO_noerr) then
write(iulog,*)'pio error from ',trim(subname),':',trim(cstring),': ERROR = ',ret
call endrun
()
end if
end subroutine check_ret_pio
#endif
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_create
!
! !INTERFACE:
subroutine ncd_create(filename,mode,ncid,cstring,usepio) 3,3
!
! !DESCRIPTION:
! create netcdf file
!
! !USES:
use clm_varctl
, only : outnc_large_files
! !ARGUMENTS:
implicit none
character(len=*),intent(in) :: filename ! file to open
integer ,intent(in) :: mode ! nf_create mode
integer ,intent(out):: ncid ! netcdf file id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
integer :: stride ! pe stride for num_iotasks
integer :: base ! base pe for iotasks
integer :: filemode ! filemode
integer :: iotype ! type of output file
character(len=*),parameter :: subname='ncd_create' ! subroutine name
!-----------------------------------------------------------------------
ncid = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call PIO_setDebugLevel(ncd_pio_DebugLevel)
pio_num_iotasks = min(ncd_pio_num_iotasks,npes)
pio_num_aggregator = npes
if (ncd_pio_UseRearranger) then
if (ncd_pio_SerialCDF) then
iotype = iotype_netcdf_rearrange ! serial netcdf no rearrange
else
iotype = iotype_pnetcdf_rearrange ! parallel netcdf no rearrange
endif
else
if (ncd_pio_SerialCDF) then
iotype = iotype_netcdf ! serial netcdf w/ rearrange
else
iotype = iotype_pnetcdf ! parallel netcdf w/ rearrange
endif
endif
!tcx if (ncd_pio_IODOF_rootonly) pio_num_iotasks = 1
base = 0
stride = max(npes/pio_num_iotasks,1) ! regular pe stride
call PIO_initFile(iam, mpicom, &
pio_num_iotasks,pio_num_aggregator, stride,iotype,pio_File,base=base)
call check_ret_pio
(PIO_CreateFile(pio_File,trim(filename)), &
trim(subname)//':'//trim(cstring))
pio_io_rank = pio_File%io_rank
pio_IOproc = pio_File%IOproc
if (masterproc) then
write(iulog,*) trim(subname),' iam = ',iam,'iorank=',pio_io_rank, &
'ioproc=',pio_IOproc,'iotasks=',pio_num_iotasks, &
'naggr=',pio_num_aggregator,'base/stride=',base,stride,'iotype=',iotype
endif
#endif
else
if (.not. masterproc) return
if ( outnc_large_files )then
filemode = ior(mode,nf_64bit_offset)
else
filemode = mode
end if
call check_ret
(nf_create(trim(filename),filemode,ncid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_create
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_open
!
! !INTERFACE:
subroutine ncd_open(filename,mode,ncid,cstring,usepio) 3,2
!
! !DESCRIPTION:
! open netcdf file
!
! !ARGUMENTS:
implicit none
character(len=*),intent(in) :: filename ! file to open
integer ,intent(in) :: mode ! nf_create mode
integer ,intent(out):: ncid ! netcdf file id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_open' ! subroutine name
!-----------------------------------------------------------------------
ncid = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call PIO_setDebugLevel(ncd_pio_DebugLevel)
call check_ret_pio
(PIO_OpenFile(pio_File,trim(filename)), &
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_open(trim(filename),mode,ncid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_open
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_close
!
! !INTERFACE:
subroutine ncd_close(ncid,cstring,usepio) 3,1
!
! !DESCRIPTION:
! close netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_close' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call PIO_CloseFile(pio_File)
#endif
else
if (.not. masterproc) return
call check_ret
(nf_close(ncid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_close
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_redef
!
! !INTERFACE:
subroutine ncd_redef(ncid,cstring,usepio),1
!
! !DESCRIPTION:
! redef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_redef' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (masterproc) write(iulog,*) trim(subname),':',trim(cstring),' WARNING: pio not implemented'
#endif
else
if (.not. masterproc) return
call check_ret
(nf_redef(ncid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_redef
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_enddef
!
! !INTERFACE:
subroutine ncd_enddef(ncid,cstring,usepio) 1,2
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_enddef' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_enddef(pio_File),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_enddef(ncid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_enddef
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_setfill
!
! !INTERFACE:
subroutine ncd_setfill(ncid,mode,old_mode,cstring,usepio) 1,1
!
! !DESCRIPTION:
! setfill netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: mode ! fill mode
integer ,intent(out):: old_mode ! old mode
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_setfill' ! subroutine name
!-----------------------------------------------------------------------
old_mode = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (masterproc) write(iulog,*) trim(subname),':',trim(cstring),' WARNING: pio not implemented'
#endif
else
if (.not. masterproc) return
call check_ret
(nf_set_fill(ncid,mode,old_mode), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_setfill
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqdid
!
! !INTERFACE:
subroutine ncd_inqdid(ncid,name,dimid,cstring,usepio) 5,2
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: name ! dimension name
integer ,intent(out):: dimid ! dimension id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqdid' ! subroutine name
!-----------------------------------------------------------------------
dimid = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_inq_dimid(pio_File,name,dimid),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_dimid(ncid,name,dimid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqdid
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqdlen
!
! !INTERFACE:
subroutine ncd_inqdlen(ncid,dimid,len,cstring,usepio) 13,2
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: dimid ! dimension id
integer ,intent(out):: len ! dimension len
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqdlen' ! subroutine name
!-----------------------------------------------------------------------
len = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_inq_dimlen(pio_File,dimid,len),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_dimlen(ncid,dimid,len), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqdlen
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqdname
!
! !INTERFACE:
subroutine ncd_inqdname(ncid,dimid,dname,cstring,usepio) 9,2
!
! !DESCRIPTION:
! inquire dim name
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: dimid ! dimension id
character(len=*),intent(out):: dname ! dimension name
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqdname' ! subroutine name
!-----------------------------------------------------------------------
dname = ''
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_inq_dimname(pio_File,dimid,dname),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_dimname(ncid,dimid,dname), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqdname
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqvdesc
!
! !INTERFACE:
subroutine ncd_inqvdesc(name,vdnum,cstring,usepio) 14
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
character(len=*),intent(in) :: name ! variable name
integer ,intent(out):: vdnum ! vardesc num
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
logical :: found ! search flag
integer :: n
character(len=*),parameter :: subname='ncd_inqvdesc' ! subroutine name
!-----------------------------------------------------------------------
vdnum = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
n = 1
found = .false.
do while (n <= pio_num_vardesc .and. .not.found)
if (trim(name) == trim(pio_vardesc_list(n)%name)) then
found = .true.
vdnum = n
endif
n = n + 1
enddo
#endif
else
! do nothing
endif
end subroutine ncd_inqvdesc
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqiodesc
!
! !INTERFACE:
subroutine ncd_inqiodesc(ndims,dimids,type,iodnum,cstring,usepio) 1
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ndims ! number of dims
integer ,intent(in) :: dimids(:) ! dimids
integer ,intent(in) :: type ! data type
integer ,intent(out):: iodnum ! iodesc num
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
logical :: found ! search flag
integer :: n,m
character(len=*),parameter :: subname='ncd_inqiodesc' ! subroutine name
!-----------------------------------------------------------------------
iodnum = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
n = 1
found = .false.
do while (n <= pio_num_iodesc .and. .not.found)
if (ndims == pio_iodesc_list(n)%ndims .and. type == pio_iodesc_list(n)%type) then
found = .true.
do m = 1,ndims
if (dimids(m) /= pio_iodesc_list(n)%dimids(m)) then
found = .false.
endif
enddo
endif
if (found) then
iodnum = n
endif
n = n + 1
enddo
#endif
else
! do nothing
endif
end subroutine ncd_inqiodesc
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqvid
!
! !INTERFACE:
subroutine ncd_inqvid(ncid,name,varid,cstring,readvar,usepio,pio_vardesc) 27,2
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: name ! variable name
integer ,intent(out):: varid ! variable id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(out):: readvar ! does variable exist
logical,optional,intent(in) :: usepio ! use pio lib
#if (defined BUILDPIO)
type(Var_desc_t),optional,intent(inout):: pio_varDesc
#else
integer,optional,intent(out) :: pio_varDesc ! dummy
#endif
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
integer :: ret ! return code
character(len=*),parameter :: subname='ncd_inqvid' ! subroutine name
!-----------------------------------------------------------------------
varid = -1
if (present(readvar)) then
readvar = .false.
endif
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (present(readvar)) then
ret = PIO_inq_varid(pio_File,name,pio_varDesc)
if (ret/=PIO_noerr) then
if (masterproc) write(iulog,*) trim(subname),': variable ',trim(name),' is not on dataset'
readvar = .false.
else
readvar = .true.
end if
else
call check_ret_pio
(PIO_inq_varid(pio_File,name,pio_varDesc), &
trim(subname)//':'//trim(cstring))
endif
varid = pio_varDesc%varid
#else
pio_varDesc = -1
#endif
else
if (.not. masterproc) return
if (present(readvar)) then
ret = nf_inq_varid (ncid, name, varid)
if (ret/=NF_NOERR) then
if (masterproc) write(iulog,*) trim(subname),': variable ',trim(name),' is not on dataset'
readvar = .false.
else
readvar = .true.
end if
else
call check_ret
(nf_inq_varid(ncid,name,varid), &
trim(subname)//':'//trim(cstring))
endif
endif
end subroutine ncd_inqvid
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqvdims
!
! !INTERFACE:
subroutine ncd_inqvdims(ncid,varid,ndims,cstring,usepio,pio_varDesc) 18,3
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! variable id
integer ,intent(out):: ndims ! variable ndims
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
#if (defined BUILDPIO)
type(Var_desc_t),optional,intent(inout):: pio_varDesc
#else
integer,optional,intent(in) :: pio_varDesc ! dummy
#endif
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqvdims' ! subroutine name
!-----------------------------------------------------------------------
ndims = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (.not.present(pio_varDesc)) then
write(iulog,*) trim(subname),' ERROR pio_varDesc must be an argument'
call endrun
()
endif
call check_ret_pio
(PIO_inq_varndims(pio_File,pio_varDesc,ndims),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_varndims(ncid,varid,ndims), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqvdims
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqvname
!
! !INTERFACE:
subroutine ncd_inqvname(ncid,varid,vname,cstring,usepio,pio_varDesc) 18,3
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! variable id
character(len=*),intent(out):: vname ! variable vname
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
#if (defined BUILDPIO)
type(Var_desc_t),optional,intent(inout):: pio_varDesc
#else
integer,optional,intent(in) :: pio_varDesc ! dummy
#endif
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqvname' ! subroutine name
!-----------------------------------------------------------------------
vname = ''
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (.not.present(pio_varDesc)) then
write(iulog,*) trim(subname),' ERROR pio_varDesc must be an argument'
call endrun
()
endif
call check_ret_pio
(PIO_inq_varname(pio_File,pio_varDesc,vname),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_varname(ncid,varid,vname), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqvname
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_inqvdids
!
! !INTERFACE:
subroutine ncd_inqvdids(ncid,varid,dids,cstring,usepio,pio_varDesc) 18,3
!
! !DESCRIPTION:
! enddef netcdf file
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! variable id
integer ,intent(out):: dids(:) ! variable dids
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
#if (defined BUILDPIO)
type(Var_desc_t),optional,intent(inout):: pio_varDesc
#else
integer,optional,intent(in) :: pio_varDesc ! dummy
#endif
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_inqvdids' ! subroutine name
!-----------------------------------------------------------------------
dids = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (.not.present(pio_varDesc)) then
write(iulog,*) trim(subname),' ERROR pio_varDesc must be an argument'
call endrun
()
endif
call check_ret_pio
(PIO_inq_vardimid(pio_File,pio_varDesc,dids),&
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_inq_vardimid(ncid,varid,dids), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_inqvdids
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_putatt_int
!
! !INTERFACE:
subroutine ncd_putatt_int(ncid,varid,attrib,value,cstring,xtype,usepio) 1,2
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! netcdf var id
character(len=*),intent(in) :: attrib ! netcdf attrib
integer ,intent(in) :: value ! netcdf attrib value
character(len=*),intent(in) :: cstring ! comment string
integer,optional,intent(in) :: xtype ! netcdf data type
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
integer :: lxtype
character(len=*),parameter :: subname='ncd_putatt_int' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_att(pio_File,varid,trim(attrib),value), &
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
if (present(xtype)) then
lxtype = xtype
else
lxtype = nf_int
endif
call check_ret
(nf_put_att_int(ncid, varid, trim(attrib), lxtype, 1, value), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_putatt_int
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_putatt_char
!
! !INTERFACE:
subroutine ncd_putatt_char(ncid,varid,attrib,value,cstring,xtype,usepio) 1,2
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! netcdf var id
character(len=*),intent(in) :: attrib ! netcdf attrib
character(len=*),intent(in) :: value ! netcdf attrib value
character(len=*),intent(in) :: cstring ! comment string
integer,optional,intent(in) :: xtype ! netcdf data type
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_putatt_char' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_att(pio_File,varid,trim(attrib),value), &
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_put_att_text(ncid, varid, trim(attrib), len_trim(value), value), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_putatt_char
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_putatt_real
!
! !INTERFACE:
subroutine ncd_putatt_real(ncid,varid,attrib,value,cstring,xtype,usepio) 1,3
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
integer ,intent(in) :: varid ! netcdf var id
character(len=*),intent(in) :: attrib ! netcdf attrib
real(r8) ,intent(in) :: value ! netcdf attrib value
character(len=*),intent(in) :: cstring ! comment string
integer,optional,intent(in) :: xtype ! netcdf data type
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
integer :: lxtype
real*4 :: value4
character(len=*),parameter :: subname='ncd_putatt_real' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
value4 = value
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
if (lxtype == nf_double) then
call check_ret_pio
(PIO_put_att(pio_File,varid,trim(attrib),value), &
trim(subname)//':'//trim(cstring))
else
call check_ret_pio
(PIO_put_att(pio_File,varid,trim(attrib),value4), &
trim(subname)//':'//trim(cstring))
endif
#endif
else
if (.not. masterproc) return
if (present(xtype)) then
lxtype = xtype
else
lxtype = nf_double
endif
call check_ret
(nf_put_att_double(ncid, varid, trim(attrib), lxtype, 1, value), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_putatt_real
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_defdim
!
! !INTERFACE:
subroutine ncd_defdim(ncid,attrib,value,dimid,cstring,usepio) 23,2
!
! !DESCRIPTION:
! Check return status from netcdf call
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! netcdf file id
character(len=*),intent(in) :: attrib ! netcdf attrib
integer ,intent(in) :: value ! netcdf attrib value
integer ,intent(out):: dimid ! netcdf dimension id
character(len=*),intent(in) :: cstring ! comment string
logical,optional,intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_defdim' ! subroutine name
!-----------------------------------------------------------------------
dimid = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(pio_def_dim(pio_File,attrib,value,dimid), &
trim(subname)//':'//trim(cstring))
#endif
else
if (.not. masterproc) return
call check_ret
(nf_def_dim(ncid, trim(attrib), value, dimid), &
trim(subname)//':'//trim(cstring))
endif
end subroutine ncd_defdim
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_defvar_bynf
!
! !INTERFACE:
subroutine ncd_defvar_bynf(ncid, varname, xtype, ndims, dimid, varid, & 2,17
cstring, long_name, units, cell_method, missing_value, fill_value, &
imissing_value, ifill_value, usepio)
!
! !DESCRIPTION:
! Define a netcdf variable
!
! !ARGUMENTS:
implicit none
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(in) :: xtype ! external type
integer , intent(in) :: ndims ! number of dims
integer , intent(in), optional :: dimid(:) ! dimids
integer , intent(out) :: varid ! returned var id
character(len=*), intent(in), optional :: cstring ! caller string
character(len=*), intent(in), optional :: long_name ! attribute
character(len=*), intent(in), optional :: units ! attribute
character(len=*), intent(in), optional :: cell_method ! attribute
real(r8) , intent(in), optional :: missing_value ! attribute for real
real(r8) , intent(in), optional :: fill_value ! attribute for real
integer , intent(in), optional :: imissing_value ! attribute for int
integer , intent(in), optional :: ifill_value ! attribute for int
logical , intent(in), optional :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n ! indices
character(len=256) :: str ! temporary
character(len=256) :: lsubname ! temporary
integer :: ldimid(4) ! local dimid
integer :: dimid0(1) ! local dimid
integer :: vdnum ! vardesc num
integer :: iodnum ! iodesc num
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_defvar_bynf' ! subroutine name
!-----------------------------------------------------------------------
varid = -1
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (present(cstring)) then
lsubname = trim(subname)//':'//trim(cstring)
else
lsubname = trim(subname)
endif
dimid0 = 0
ldimid = 0
if (present(dimid)) then
ldimid(1:ndims) = dimid(1:ndims)
else ! ndims must be zero if dimid not present
if (ndims /= 0) then
write(iulog,*) trim(lsubname),' ERROR: dimid not supplied and ndims ne 0 ',trim(varname),ndims
call endrun
()
endif
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
write(iulog,*) trim(subname),' ',trim(varname),xtype,ndims,ldimid(1:ndims)
endif
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(trim(varname),vdnum,lsubname,usepio=lusepio)
if (vdnum < 1) then
pio_num_vardesc = pio_num_vardesc + 1
if (pio_num_vardesc > pio_max_vardesc) then
write(iulog,*) trim(subname),' ERROR num_vardesc gt max_vardesc ',trim(varname),pio_max_vardesc
call endrun
()
endif
vdnum = pio_num_vardesc
pio_varDesc_list(vdnum)%name = trim(varname)
call ncd_inqiodesc
(ndims,ldimid,xtype,iodnum,lsubname,usepio=lusepio)
if (iodnum < 1) then
! generate iodesc
pio_num_iodesc = pio_num_iodesc + 1
if (pio_num_iodesc > pio_max_iodesc) then
write(iulog,*) trim(subname),' ERROR num_iodesc gt max_iodesc ',trim(varname),pio_max_iodesc
call endrun
()
endif
iodnum = pio_num_iodesc
pio_iodesc_list(iodnum)%ndims = ndims
pio_iodesc_list(iodnum)%dimids = 0
pio_iodesc_list(iodnum)%dimids(1:ndims) = ldimid(1:ndims)
pio_iodesc_list(iodnum)%type = xtype
pio_iodesc_list(iodnum)%set = .false.
!tcx if (masterproc .and. debug > 1) then
if (masterproc) then
write(iulog,*) trim(subname),' creating iodesc at ',trim(varname),vdnum,iodnum,ndims,ldimid(1:ndims),xtype
endif
else
if (iodnum > pio_num_iodesc) then
write(iulog,*) trim(lsubname),' ERROR: iodnum out of range ',iodnum,pio_num_iodesc
call endrun
()
endif
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' creating vardesc for ',trim(varname),vdnum,iodnum
endif
pio_varDesc_list(vdnum)%iodnum = iodnum
call pio_setVarDesc(pio_iodesc_list(iodnum)%pio_iodesc,pio_vardesc_list(vdnum)%pio_vardesc)
else ! vardesc already exists
if (vdnum > pio_num_vardesc) then
write(iulog,*) trim(lsubname),' ERROR: vdnum out of range ',vdnum,pio_num_vardesc
call endrun
()
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' vardesc exists for ',trim(varname),vdnum
endif
endif
if (present(dimid)) then
call check_ret_pio
(PIO_def_var(pio_File,trim(varname),xtype, &
dimid(1:ndims), pio_varDesc_list(vdnum)%pio_varDesc), &
trim(lsubname))
else
call check_ret_pio
(PIO_def_var(pio_File,trim(varname),xtype, &
dimid0 , pio_varDesc_list(vdnum)%pio_varDesc), &
trim(lsubname))
endif
varid = pio_varDesc_list(vdnum)%pio_varDesc%varid
#endif
else
if (.not. masterproc) return
! Define variable
call check_ret
(nf_def_var(ncid, trim(varname), xtype, ndims, ldimid, varid), lsubname)
endif
if (present(long_name)) then
call ncd_putatt
(ncid, varid, 'long_name', trim(long_name), lsubname, usepio=lusepio)
end if
if (present(units)) then
call ncd_putatt
(ncid, varid, 'units', trim(units), lsubname, usepio=lusepio)
end if
if (present(cell_method)) then
str = 'time: ' // trim(cell_method)
call ncd_putatt
(ncid, varid, 'cell_methods', trim(str), lsubname, usepio=lusepio)
end if
if (present(fill_value)) then
call ncd_putatt
(ncid, varid, '_FillValue', fill_value, lsubname, xtype, usepio=lusepio)
end if
if (present(missing_value)) then
call ncd_putatt
(ncid, varid, 'missing_value', missing_value, lsubname, xtype, usepio=lusepio)
end if
if (present(ifill_value)) then
call ncd_putatt
(ncid, varid, '_FillValue', ifill_value, lsubname, xtype, usepio=lusepio)
end if
if (present(imissing_value)) then
call ncd_putatt
(ncid, varid, 'missing_value', imissing_value, lsubname, xtype, usepio=lusepio)
end if
end subroutine ncd_defvar_bynf
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_defvar_bygrid
!
! !INTERFACE:
subroutine ncd_defvar_bygrid(ncid, varname, xtype, & 1,13
dim1name, dim2name, dim3name, dim4name, dim5name, &
long_name, units, cell_method, missing_value, fill_value, &
imissing_value, ifill_value, usepio)
!
! !DESCRIPTION:
! Define a netcdf variable
!
! !ARGUMENTS:
implicit none
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(in) :: xtype ! external type
character(len=*), intent(in), optional :: dim1name ! dimension name
character(len=*), intent(in), optional :: dim2name ! dimension name
character(len=*), intent(in), optional :: dim3name ! dimension name
character(len=*), intent(in), optional :: dim4name ! dimension name
character(len=*), intent(in), optional :: dim5name ! dimension name
character(len=*), intent(in), optional :: long_name ! attribute
character(len=*), intent(in), optional :: units ! attribute
character(len=*), intent(in), optional :: cell_method ! attribute
real(r8) , intent(in), optional :: missing_value ! attribute for real
real(r8) , intent(in), optional :: fill_value ! attribute for real
integer , intent(in), optional :: imissing_value ! attribute for int
integer , intent(in), optional :: ifill_value ! attribute for int
logical , intent(in), optional :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n ! indices
integer :: ndims ! dimension counter
integer :: dimid(5) ! dimension ids
integer :: varid ! variable id
integer :: itmp ! temporary
logical :: switchdim ! true=> permute dim1 and dim2 for output
logical :: lusepio ! local usepio variable
character(len=256) :: str ! temporary
character(len=*),parameter :: subname='ncd_defvar_bygrid' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
dimid(:) = 0
if (masterproc .and. debug > 1) write(iulog,*) trim(subname),lusepio
if (lusepio) then
! continue
else
if (.not. masterproc) return
endif
! Determine dimension ids for variable
if (present(dim1name)) then
call ncd_inqdid
(ncid, dim1name, dimid(1), subname, lusepio)
end if
if (present(dim2name)) then
call ncd_inqdid
(ncid, dim2name, dimid(2), subname, lusepio)
end if
if (present(dim3name)) then
call ncd_inqdid
(ncid, dim3name, dimid(3), subname, lusepio)
end if
if (present(dim4name)) then
call ncd_inqdid
(ncid, dim4name, dimid(4), subname, lusepio)
end if
if (present(dim5name)) then
call ncd_inqdid
(ncid, dim5name, dimid(5), subname, lusepio)
end if
#if (defined SWITCH_DIMS)
! Permute dim1 and dim2 if necessary
! (If first dimension corresponds to a clmtype 1d type and
! if second dimension is a level dimension)
if (present(dim1name) .and. present(dim2name)) then
if (dim1name=='gridcell' .or. dim1name=='landunit' .or. &
dim1name=='column' .or. dim1name=='pft') then
switchdim = .false.
if (dim2name(1:3)=='lev' .or. dim2name(1:3)=='num') then
switchdim = .true.
end if
#if (defined CASA)
if (dim2name=='npools' .or. dim2name=='nlive') then
switchdim = .true.
end if
#endif
if (switchdim) then
itmp = dimid(2)
dimid(2) = dimid(1)
dimid(1) = itmp
endif
end if
end if
#endif
! Define variable
ndims = 0
if (present(dim1name)) then
do n = 1, size(dimid)
if (dimid(n) /= 0) ndims = ndims + 1
end do
endif
call ncd_defvar_bynf
(ncid,varname,xtype,ndims,dimid,varid,subname,usepio=lusepio)
if (present(long_name)) then
call ncd_putatt
(ncid, varid, 'long_name', trim(long_name), subname, usepio=lusepio)
end if
if (present(units)) then
call ncd_putatt
(ncid, varid, 'units', trim(units), subname, usepio=lusepio)
end if
if (present(cell_method)) then
str = 'time: ' // trim(cell_method)
call ncd_putatt
(ncid, varid, 'cell_methods', trim(str), subname, usepio=lusepio)
end if
if (present(fill_value)) then
call ncd_putatt
(ncid, varid, '_FillValue', fill_value, subname, xtype, usepio=lusepio)
end if
if (present(missing_value)) then
call ncd_putatt
(ncid, varid, 'missing_value', missing_value, subname, xtype, usepio=lusepio)
end if
if (present(ifill_value)) then
call ncd_putatt
(ncid, varid, '_FillValue', ifill_value, subname, xtype, usepio=lusepio)
end if
if (present(imissing_value)) then
call ncd_putatt
(ncid, varid, 'missing_value', imissing_value, subname, xtype, usepio=lusepio)
end if
end subroutine ncd_defvar_bygrid
!-----------------------------------------------------------------------
!***** begin include ncdio_local_subs.inc *****
! this next section has been autogenerated from
! --- gen_ncdio_local_subs.csh ---
! and manually included. this section ends at "end include ..."
!-----------------------------------------------------------------------
! #include <ncdio_local_subs.inc>
!-----------------------------------------------------------------------
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_int_1d
!
! !INTERFACE:
subroutine ncd_iolocal_int_1d(varname, data, dim1name, & 1,5
flag, ncid, nlonxy, nlatxy, nt, readvar, missing, usepio)
!
! !DESCRIPTION:
! I/O for 1d int field
!
! !USES:
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , pointer :: data(:) ! local decomposition data
character(len=*), intent(in) :: dim1name ! dimension name
integer , optional, intent(in) :: nlonxy ! 2d longitude size
integer , optional, intent(in) :: nlatxy ! 2d latitude size
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(out):: readvar ! true => variable is on initial dataset (read only)
integer , optional, intent(in) :: missing ! missing value
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: dims ! dimensions
integer :: gsize ! size of global array
integer :: ier ! error status
integer :: start(3) ! starting indices for netcdf field
integer :: count(3) ! count values for netcdf field
integer :: lmissing ! local missing value
logical :: lusepio ! local usepio variable
character(len=8) :: clmlevel ! clmlevel
character(len=*),parameter :: subname='ncd_iolocal_int_1d' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),lusepio
endif
if ((present(nlonxy) .and. .not.present(nlatxy)) .or. &
(present(nlatxy) .and. .not.present(nlonxy))) then
write(iulog,*) trim(subname),' error nlonxy/nlatxy must be both or neither present '
call endrun
()
endif
if (present(missing)) then
lmissing = missing
else
lmissing = ispval
endif
clmlevel = dim1name
if (present(nlonxy) .and. present(nlatxy)) then
if (dim1name == nameg .or. dim1name == grlnd) then
clmlevel = grlnd
elseif (dim1name == allrof .or. dim1name == gratm) then
! continue, acceptable and default behavior for now
else
if (masterproc) write(iulog,*) trim(subname),' warning incorrect use of dim1name and nlonxy/nlatxy ', &
trim(dim1name),nlonxy,nlatxy
endif
endif
gsize = get_clmlevel_gsize
(clmlevel)
start = 1
count = 1
call get_clmlevel_dsize
(clmlevel,dims,count(1),count(2))
if (dims == 1) then
if (present(nt)) then
start(2) = nt
endif
elseif (dims == 2) then
if (present(nt)) then
start(3) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
call ncd_iolocal_gs_int1d
(ncid, varname, flag, data, clmlevel, start, count, ier, lmissing, usepio=lusepio)
if (present(readvar)) then
readvar = .false.
if (ier == 0) readvar = .true.
endif
end subroutine ncd_iolocal_int_1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_int_2d
!
! !INTERFACE:
subroutine ncd_iolocal_int_2d(varname, data, dim1name, dim2name, & 1,10
lowerb2, upperb2, flag, ncid, nlonxy, nlatxy, nt, readvar, missing, usepio)
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial integer field out to netCDF file
!
! !USES:
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , pointer :: data(:,:) ! local decomposition input data
character(len=*), intent(in) :: dim1name ! dimension 1 name
character(len=*), intent(in) :: dim2name ! dimension 2 name
integer , optional, intent(in) :: nlonxy ! 2d longitude size
integer , optional, intent(in) :: nlatxy ! 2d latitude size
integer , optional, intent(in) :: nt ! time sample index
integer , optional, intent(in) :: lowerb2,upperb2 ! lower and upper bounds of second dimension
logical , optional, intent(out):: readvar ! true => variable is on initial dataset (read only)
integer , optional, intent(in) :: missing ! missing value
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: k ! index
integer :: dims ! dimensions
integer :: gsize ! size of global array
integer :: ier ! error status
integer :: start(4) ! starting indices for netcdf field
integer :: count(4) ! count values for netcdf field
integer :: lb1,ub1 ! lower/upper bound of dim 1
integer :: lb2,ub2 ! lower/upper bound of dim 2
integer :: lmissing ! local missing value
logical :: lusepio ! local usepio variable
integer ,pointer :: data1d(:) ! 1 level data
character(len=8) :: clmlevel ! clmlevel
character(len=*),parameter :: subname='ncd_iolocal_int_2d' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (lusepio .and. ncd_lowmem2d) then
write(iulog,*) trim(subname),' ERROR usepio and ncd_lowmem2d are both true'
call endrun
()
endif
if (.not.lusepio .and. .not.ncd_lowmem2d) then
write(iulog,*) trim(subname),' ERROR ncd_lowmem2d must be true with non pio runs. ',&
' This error will be corrected in the future '
call endrun
()
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),lusepio
endif
if ((present(nlonxy) .and. .not.present(nlatxy)) .or. &
(present(nlatxy) .and. .not.present(nlonxy))) then
write(iulog,*) trim(subname),' error nlonxy/nlatxy must be both or neither present '
call endrun
()
endif
lb1 = lbound(data, dim=1)
ub1 = ubound(data, dim=1)
if (present(lowerb2)) then
lb2 = lowerb2
else
lb2 = lbound(data, dim=2)
end if
if (present(upperb2)) then
ub2 = upperb2
else
ub2 = ubound(data, dim=2)
end if
if (present(missing)) then
lmissing = missing
else
lmissing = ispval
endif
clmlevel = dim1name
if (present(nlonxy) .and. present(nlatxy)) then
if (dim1name == nameg .or. dim1name == grlnd) then
clmlevel = grlnd
else
write(iulog,*) trim(subname),' error in dim1name and nlonxy/nlatxy ',trim(dim1name),nlonxy,nlatxy
call endrun
()
endif
endif
gsize = get_clmlevel_gsize
(clmlevel)
start = 1
count = 1
call get_clmlevel_dsize
(clmlevel,dims,count(1),count(2))
if (ncd_lowmem2d) then
allocate(data1d(lb1:ub1))
do k = lb2,ub2
if (dims == 1) then
#if (defined SWITCH_DIMS)
start(1) = k-lb2+1
count(1) = 1
count(2) = gsize
#else
count(1) = gsize
start(2) = k-lb2+1
count(2) = 1
#endif
if (present(nt)) then
start(3) = nt
endif
elseif (dims == 2) then
! count set by dsize ok
start(3) = k-lb2+1
if (present(nt)) then
start(4) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
if (flag == 'write') data1d(:) = data(:,k)
call ncd_iolocal_gs_int1d
(ncid, varname, flag, data1d, clmlevel, start, count, ier, lmissing, usepio=lusepio)
if (flag == 'read' .and. ier == 0 ) data(:,k) = data1d(:)
enddo
deallocate(data1d)
else
if (dims == 1) then
#if (defined SWITCH_DIMS)
start(1) = 1
count(1) = ub2-lb2+1
count(2) = gsize
#else
count(1) = gsize
start(2) = 1
count(2) = ub2-lb2+1
#endif
if (present(nt)) then
start(3) = nt
endif
elseif (dims == 2) then
! count set by dsize ok
start(3) = 1
count(3) = ub2-lb2+1
if (present(nt)) then
start(4) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
call ncd_iolocal_gs_int2d
(ncid, varname, flag, data, clmlevel, start, count, ier, lmissing, usepio=lusepio)
endif
if (present(readvar)) then
readvar = .false.
if (ier == 0) readvar = .true.
endif
end subroutine ncd_iolocal_int_2d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_gs_int1d
!
! !INTERFACE:
subroutine ncd_iolocal_gs_int1d(ncid, varname, flag, data, clmlevel, start, count, status, missing, usepio) 3,20
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial real field out to netCDF file
!
! !USES:
use spmdGathScatMod
, only : scatter_data_from_master, gather_data_to_master
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! input unit
character(len=*) ,intent(in) :: varname ! variable name
character(len=*) ,intent(in) :: flag ! 'read' or 'write'
integer ,pointer :: data(:) ! local decomposition input data (out)
character(len=*) ,intent(in) :: clmlevel ! type of grid
integer, optional,intent(in) :: start(:) ! netcdf start index
integer, optional,intent(in) :: count(:) ! netcdf count index
integer, optional,intent(out) :: status ! return code
integer ,optional,intent(in) :: missing ! missing value
logical, optional,intent(in) :: usepio ! use pio lib
!--- rcodes:
! 0 : success
! -99 : general error
! -5 : var not found on read
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n
integer , pointer :: arrayg(:)
integer :: gsize ! array global size from gsmap
integer :: lstart(4),lcount(4) ! local start/count arrays
integer :: varid ! varid
integer :: ndims ! ndims for var
integer :: dids(4) ! dim ids
character(len=32) :: dname(4) ! dim names
integer :: dlen(4) ! dim lens
#if (defined BUILDPIO)
type(pio_vardesc_plus_type),pointer :: pio_vardesc_plus
type(pio_iodesc_plus_type) ,pointer :: pio_iodesc_plus
integer :: vdnum ! vardesc num in list
integer :: basetype ! pio initdecomp info
integer :: lenblocks ! pio initdecomp info
integer :: dims(4) ! pio initdecomp info
integer :: iodnum ! iodesc num in list
integer,pointer :: compDOF(:)
integer,pointer :: ioDOF(:)
integer(pio_offset),pointer :: pstart(:),pcount(:)
integer ,pointer :: data1d(:) ! 1d copy of data starting at index 1
integer :: n1,n1b,n1e,n1s
#endif
logical :: varpresent ! if true, variable is on tape
integer :: rcode ! local return code
integer :: ier ! error code
integer :: data_offset ! offset to single grid point for column model
integer :: ndata ! count of pft's or columns to read
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_iolocal_gs_int1d' ! subroutine name
!-----------------------------------------------------------------------
call t_startf('ncd_lgs1d_total')
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),' ',trim(clmlevel),lusepio
endif
rcode = 0
lstart = 1
lcount = 1
if (present(start).and.present(count)) then
lstart(1:size(start)) = start(1:size(start))
lcount(1:size(count)) = count(1:size(count))
endif
gsize = get_clmlevel_gsize
(clmlevel)
if (flag == 'read') then
if (masterproc) then
allocate(arrayg(gsize))
call check_var
(ncid, varname, varid, varpresent)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,clmlevel,lstart,lcount)
call check_ret
(nf_get_vara_int(ncid, varid, lstart, lcount, arrayg), subname)
else
if (present(start).and.present(count)) then
call check_ret
(nf_get_vara_int(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_get_var_int(ncid, varid, arrayg), subname)
endif
endif
else
rcode = -5
endif
endif
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if ( varpresent ) call scatter_data_from_master
(data,arrayg,clmlevel)
if (masterproc) then
deallocate(arrayg)
endif
elseif (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call t_startf('ncd_lgs1d_wptotal')
call ncd_inqvdesc
(varname,vdnum,subname,usepio=lusepio)
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
pio_vardesc_plus => pio_vardesc_list(vdnum)
iodnum = pio_vardesc_plus%iodnum
if (iodnum < 1 .or. iodnum > pio_num_iodesc) then
write(iulog,*) trim(subname),' ERROR in iodnum from vardesc ',trim(varname),iodnum
call endrun
()
endif
pio_iodesc_plus => pio_iodesc_list(iodnum)
!------------------------
!--- setup iodesc if it's not set yet ---
!------------------------
if (.not. pio_iodesc_plus%set) then
call t_startf('ncd_lgs1d_wpsetdof')
baseTYPE = MPI_INTEGER
dims(:) = 1
ndims = pio_iodesc_plus%ndims
do n = 1,ndims
call ncd_inqdlen
(ncid,pio_iodesc_plus%dimids(n),dims(n),trim(subname),usepio=lusepio)
if (dims(n) == 0) dims(n) = 1 ! sometimes for time axis?
enddo
lenBLOCKS = 1
call ncd_setDOF
(clmlevel,dims,compDOF,ioDOF,pstart,pcount)
!--- pio call ---
if (ncd_pio_UseBoxRearr) then
call pio_initDecomp(pio_File,baseTYPE,dims,compDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
else
call pio_initDecomp(pio_File,baseTYPE,dims,lenBLOCKS,compDOF,ioDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
endif
deallocate(compDOF)
deallocate(IODOF)
deallocate(pstart)
deallocate(pcount)
pio_iodesc_plus%set = .true.
call t_stopf('ncd_lgs1d_wpsetdof')
endif
!------------------------
!--- end setup iodesc ---
!------------------------
call pio_setVarDesc(pio_iodesc_plus%pio_iodesc,pio_vardesc_plus%pio_vardesc)
!--- copy data to 1d array ---
call t_startf('ncd_lgs1d_wpcopy')
n1b = lbound(data,dim=1)
n1e = ubound(data,dim=1)
n1s = size(data,dim=1)
allocate(data1d(n1s),stat=n)
call shr_sys_flush
(iulog)
n = 0
do n1 = n1b,n1e
n = n + 1
data1d(n) = data(n1)
enddo
call t_stopf('ncd_lgs1d_wpcopy')
call t_startf('ncd_lgs1d_wpwrit')
call PIO_write_darray(pio_File,pio_vardesc_plus%pio_varDesc,data1d,ier)
call t_stopf('ncd_lgs1d_wpwrit')
deallocate(data1d)
call t_stopf('ncd_lgs1d_wptotal')
#endif
else
call t_startf('ncd_lgs1d_wtotal')
if (masterproc) then
allocate(arrayg(gsize))
endif
call t_startf('ncd_lgs1d_wgath')
if (present(missing)) then
call gather_data_to_master
(data,arrayg,clmlevel,missing)
else
call gather_data_to_master
(data,arrayg,clmlevel)
endif
call t_stopf('ncd_lgs1d_wgath')
if (masterproc) then
call check_ret
(nf_inq_varid(ncid, varname, varid), subname)
call t_startf('ncd_lgs1d_wwrit')
if (present(start).and.present(count)) then
call check_ret
(nf_put_vara_int(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_put_var_int(ncid, varid, arrayg), subname)
endif
call t_stopf('ncd_lgs1d_wwrit')
deallocate(arrayg)
endif
call t_stopf('ncd_lgs1d_wtotal')
endif
else
if (masterproc) then
write(iulog,*) subname,' error: unsupported flag ',trim(flag)
call endrun
()
endif
endif
if (present(status)) then
call mpi_bcast(rcode, 1, MPI_INTEGER, 0, mpicom, ier)
status = rcode
endif
call t_stopf('ncd_lgs1d_total')
end subroutine ncd_iolocal_gs_int1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_gs_int2d
!
! !INTERFACE:
subroutine ncd_iolocal_gs_int2d(ncid, varname, flag, data, clmlevel, start, count, status, missing, usepio) 2,19
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial real field out to netCDF file
!
! !USES:
use spmdGathScatMod
, only : scatter_data_from_master, gather_data_to_master
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! input unit
character(len=*) ,intent(in) :: varname ! variable name
character(len=*) ,intent(in) :: flag ! 'read' or 'write'
integer ,pointer :: data(:,:) ! local decomposition input data (out)
character(len=*) ,intent(in) :: clmlevel ! type of grid
integer, optional,intent(in) :: start(:) ! netcdf start index
integer, optional,intent(in) :: count(:) ! netcdf count index
integer, optional,intent(out) :: status ! return code
integer ,optional,intent(in) :: missing ! missing value
logical, optional,intent(in) :: usepio ! use pio lib
!--- rcodes:
! 0 : success
! -99 : general error
! -5 : var not found on read
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n
integer , pointer :: arrayg(:,:)
integer :: gsize ! array global size from gsmap
integer :: ksize ! level ndims
integer :: lstart(4),lcount(4) ! local start/count arrays
logical :: varpresent ! if true, variable is on tape
integer :: varid ! varid
integer :: dids(4) ! dim ids
character(len=32) :: dname(4) ! dim names
integer :: dlen(4) ! dim lens
#if (defined BUILDPIO)
type(pio_vardesc_plus_type),pointer :: pio_vardesc_plus
type(pio_iodesc_plus_type) ,pointer :: pio_iodesc_plus
integer :: vdnum ! vardesc num in list
integer :: basetype ! pio initdecomp info
integer :: lenblocks ! pio initdecomp info
integer :: dims(4) ! pio initdecomp info
integer :: iodnum ! iodesc num in list
integer,pointer :: compDOF(:)
integer,pointer :: ioDOF(:)
integer(pio_offset),pointer :: pstart(:),pcount(:)
integer ,pointer :: data1d(:) ! 1d copy of data starting at index 1
integer :: n1,n2,n1b,n1e,n1s,n2b,n2e,n2s
#endif
integer :: rcode ! local return code
integer :: ier ! error code
integer :: data_offset ! offset to single grid point for column model
integer :: ndata ! count of pft's or columns to read
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_iolocal_gs_int2d' ! subroutine name
!-----------------------------------------------------------------------
call t_startf('ncd_lgs2d_total')
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),' ',trim(clmlevel),lusepio
endif
rcode = 0
lstart = 1
lcount = 1
if (present(start).and.present(count)) then
lstart(1:size(start)) = start(1:size(start))
lcount(1:size(count)) = count(1:size(count))
endif
gsize = get_clmlevel_gsize
(clmlevel)
ksize = size(data,dim=2)
if (flag == 'read') then
if (masterproc) then
allocate(arrayg(gsize,ksize))
call check_var
(ncid, varname, varid, varpresent)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,clmlevel,lstart,lcount)
call check_ret
(nf_get_vara_int(ncid, varid, lstart, lcount, arrayg), subname)
else
if (present(start).and.present(count)) then
call check_ret
(nf_get_vara_int(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_get_var_int(ncid, varid, arrayg), subname)
endif
endif
else
rcode = -5
endif
endif
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if ( varpresent ) call scatter_data_from_master
(data,arrayg,clmlevel)
if (masterproc) then
deallocate(arrayg)
endif
elseif (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call t_startf('ncd_lgs2d_wptotal')
call ncd_inqvdesc
(varname,vdnum,subname,usepio=lusepio)
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
pio_vardesc_plus => pio_vardesc_list(vdnum)
iodnum = pio_vardesc_plus%iodnum
if (iodnum < 1 .or. iodnum > pio_num_iodesc) then
write(iulog,*) trim(subname),' ERROR in iodnum from vardesc ',trim(varname),iodnum
call endrun
()
endif
pio_iodesc_plus => pio_iodesc_list(iodnum)
!------------------------
!--- setup iodesc if it's not set yet ---
!------------------------
if (.not. pio_iodesc_plus%set) then
call t_startf('ncd_lgs2d_wpsetdof')
baseTYPE = MPI_INTEGER
dims(:) = 1
ndims = pio_iodesc_plus%ndims
do n = 1,ndims
call ncd_inqdlen
(ncid,pio_iodesc_plus%dimids(n),dims(n),trim(subname),usepio=lusepio)
if (dims(n) == 0) dims(n) = 1 ! sometimes for time axis?
enddo
lenBLOCKS = 1
call ncd_setDOF
(clmlevel,dims,compDOF,ioDOF,pstart,pcount)
!--- pio call ---
if (ncd_pio_UseBoxRearr) then
call pio_initDecomp(pio_File,baseTYPE,dims,compDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
else
call pio_initDecomp(pio_File,baseTYPE,dims,lenBLOCKS,compDOF,ioDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
endif
deallocate(compDOF)
deallocate(IODOF)
deallocate(pstart)
deallocate(pcount)
pio_iodesc_plus%set = .true.
call t_stopf('ncd_lgs2d_wpsetdof')
endif
!------------------------
!--- end setup iodesc ---
!------------------------
call pio_setVarDesc(pio_iodesc_plus%pio_iodesc,pio_vardesc_plus%pio_vardesc)
call t_startf('ncd_lgs2d_wpcopy')
n1b = lbound(data,dim=1)
n1e = ubound(data,dim=1)
n1s = size (data,dim=1)
n2b = lbound(data,dim=2)
n2e = ubound(data,dim=2)
n2s = size (data,dim=2)
allocate(data1d(n1s*n2s),stat=n)
n = 0
do n2 = n2b,n2e
do n1 = n1b,n1e
n = n + 1
data1d(n) = data(n1,n2)
enddo
enddo
call t_stopf('ncd_lgs2d_wpcopy')
call t_startf('ncd_lgs2d_wpwrit')
call PIO_write_darray(pio_File,pio_vardesc_plus%pio_varDesc,data1d,ier)
call t_stopf('ncd_lgs2d_wpwrit')
deallocate(data1d)
call t_stopf('ncd_lgs2d_wptotal')
#endif
else
call t_startf('ncd_lgs2d_wtotal')
if (masterproc) then
allocate(arrayg(gsize,ksize))
endif
call t_startf('ncd_lgs2d_wgath')
if (present(missing)) then
call gather_data_to_master
(data,arrayg,clmlevel,missing)
else
call gather_data_to_master
(data,arrayg,clmlevel)
endif
call t_stopf('ncd_lgs2d_wgath')
if (masterproc) then
call check_ret
(nf_inq_varid(ncid, varname, varid), subname)
call t_startf('ncd_lgs2d_wwrit')
if (present(start).and.present(count)) then
call check_ret
(nf_put_vara_int(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_put_var_int(ncid, varid, arrayg), subname)
endif
call t_stopf('ncd_lgs2d_wwrit')
deallocate(arrayg)
endif
call t_stopf('ncd_lgs2d_wtotal')
endif
else
if (masterproc) then
write(iulog,*) subname,' error: unsupported flag ',trim(flag)
call endrun
()
endif
endif
if (present(status)) then
call mpi_bcast(rcode, 1, MPI_INTEGER, 0, mpicom, ier)
status = rcode
endif
call t_stopf('ncd_lgs2d_total')
end subroutine ncd_iolocal_gs_int2d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_real_1d
!
! !INTERFACE:
subroutine ncd_iolocal_real_1d(varname, data, dim1name, & 1,5
flag, ncid, nlonxy, nlatxy, nt, readvar, missing, usepio)
!
! !DESCRIPTION:
! I/O for 1d int field
!
! !USES:
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , pointer :: data(:) ! local decomposition data
character(len=*), intent(in) :: dim1name ! dimension name
integer , optional, intent(in) :: nlonxy ! 2d longitude size
integer , optional, intent(in) :: nlatxy ! 2d latitude size
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(out):: readvar ! true => variable is on initial dataset (read only)
real(r8) , optional, intent(in) :: missing ! missing value
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: dims ! dimensions
integer :: gsize ! size of global array
integer :: ier ! error status
integer :: start(3) ! starting indices for netcdf field
integer :: count(3) ! count values for netcdf field
real(r8):: lmissing ! local missing value
logical :: lusepio ! local usepio variable
character(len=8) :: clmlevel ! clmlevel
character(len=*),parameter :: subname='ncd_iolocal_real_1d' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),lusepio
endif
if ((present(nlonxy) .and. .not.present(nlatxy)) .or. &
(present(nlatxy) .and. .not.present(nlonxy))) then
write(iulog,*) trim(subname),' error nlonxy/nlatxy must be both or neither present '
call endrun
()
endif
if (present(missing)) then
lmissing = missing
else
lmissing = spval
endif
clmlevel = dim1name
if (present(nlonxy) .and. present(nlatxy)) then
if (dim1name == nameg .or. dim1name == grlnd) then
clmlevel = grlnd
elseif (dim1name == allrof .or. dim1name == gratm) then
! continue, acceptable and default behavior for now
else
if (masterproc) write(iulog,*) trim(subname),' warning incorrect use of dim1name and nlonxy/nlatxy ', &
trim(dim1name),nlonxy,nlatxy
endif
endif
gsize = get_clmlevel_gsize
(clmlevel)
start = 1
count = 1
call get_clmlevel_dsize
(clmlevel,dims,count(1),count(2))
if (dims == 1) then
if (present(nt)) then
start(2) = nt
endif
elseif (dims == 2) then
if (present(nt)) then
start(3) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
call ncd_iolocal_gs_real1d
(ncid, varname, flag, data, clmlevel, start, count, ier, lmissing, usepio=lusepio)
if (present(readvar)) then
readvar = .false.
if (ier == 0) readvar = .true.
endif
end subroutine ncd_iolocal_real_1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_real_2d
!
! !INTERFACE:
subroutine ncd_iolocal_real_2d(varname, data, dim1name, dim2name, & 1,10
lowerb2, upperb2, flag, ncid, nlonxy, nlatxy, nt, readvar, missing, usepio)
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial integer field out to netCDF file
!
! !USES:
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , pointer :: data(:,:) ! local decomposition input data
character(len=*), intent(in) :: dim1name ! dimension 1 name
character(len=*), intent(in) :: dim2name ! dimension 2 name
integer , optional, intent(in) :: nlonxy ! 2d longitude size
integer , optional, intent(in) :: nlatxy ! 2d latitude size
integer , optional, intent(in) :: nt ! time sample index
integer , optional, intent(in) :: lowerb2,upperb2 ! lower and upper bounds of second dimension
logical , optional, intent(out):: readvar ! true => variable is on initial dataset (read only)
real(r8) , optional, intent(in) :: missing ! missing value
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: k ! index
integer :: dims ! dimensions
integer :: gsize ! size of global array
integer :: ier ! error status
integer :: start(4) ! starting indices for netcdf field
integer :: count(4) ! count values for netcdf field
integer :: lb1,ub1 ! lower/upper bound of dim 1
integer :: lb2,ub2 ! lower/upper bound of dim 2
real(r8):: lmissing ! local missing value
logical :: lusepio ! local usepio variable
real(r8),pointer :: data1d(:) ! 1 level data
character(len=8) :: clmlevel ! clmlevel
character(len=*),parameter :: subname='ncd_iolocal_real_2d' ! subroutine name
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (lusepio .and. ncd_lowmem2d) then
write(iulog,*) trim(subname),' ERROR usepio and ncd_lowmem2d are both true'
call endrun
()
endif
if (.not.lusepio .and. .not.ncd_lowmem2d) then
write(iulog,*) trim(subname),' ERROR ncd_lowmem2d must be true with non pio runs. ',&
' This error will be corrected in the future '
call endrun
()
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),lusepio
endif
if ((present(nlonxy) .and. .not.present(nlatxy)) .or. &
(present(nlatxy) .and. .not.present(nlonxy))) then
write(iulog,*) trim(subname),' error nlonxy/nlatxy must be both or neither present '
call endrun
()
endif
lb1 = lbound(data, dim=1)
ub1 = ubound(data, dim=1)
if (present(lowerb2)) then
lb2 = lowerb2
else
lb2 = lbound(data, dim=2)
end if
if (present(upperb2)) then
ub2 = upperb2
else
ub2 = ubound(data, dim=2)
end if
if (present(missing)) then
lmissing = missing
else
lmissing = spval
endif
clmlevel = dim1name
if (present(nlonxy) .and. present(nlatxy)) then
if (dim1name == nameg .or. dim1name == grlnd) then
clmlevel = grlnd
else
write(iulog,*) trim(subname),' error in dim1name and nlonxy/nlatxy ',trim(dim1name),nlonxy,nlatxy
call endrun
()
endif
endif
gsize = get_clmlevel_gsize
(clmlevel)
start = 1
count = 1
call get_clmlevel_dsize
(clmlevel,dims,count(1),count(2))
if (ncd_lowmem2d) then
allocate(data1d(lb1:ub1))
do k = lb2,ub2
if (dims == 1) then
#if (defined SWITCH_DIMS)
start(1) = k-lb2+1
count(1) = 1
count(2) = gsize
#else
count(1) = gsize
start(2) = k-lb2+1
count(2) = 1
#endif
if (present(nt)) then
start(3) = nt
endif
elseif (dims == 2) then
! count set by dsize ok
start(3) = k-lb2+1
if (present(nt)) then
start(4) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
if (flag == 'write') data1d(:) = data(:,k)
call ncd_iolocal_gs_real1d
(ncid, varname, flag, data1d, clmlevel, start, count, ier, lmissing, usepio=lusepio)
if (flag == 'read' .and. ier == 0 ) data(:,k) = data1d(:)
enddo
deallocate(data1d)
else
if (dims == 1) then
#if (defined SWITCH_DIMS)
start(1) = 1
count(1) = ub2-lb2+1
count(2) = gsize
#else
count(1) = gsize
start(2) = 1
count(2) = ub2-lb2+1
#endif
if (present(nt)) then
start(3) = nt
endif
elseif (dims == 2) then
! count set by dsize ok
start(3) = 1
count(3) = ub2-lb2+1
if (present(nt)) then
start(4) = nt
endif
else
write(iulog,*) trim(subname),' error dims incorrect ',clmlevel,dims
call endrun
()
endif
call ncd_iolocal_gs_real2d
(ncid, varname, flag, data, clmlevel, start, count, ier, lmissing, usepio=lusepio)
endif
if (present(readvar)) then
readvar = .false.
if (ier == 0) readvar = .true.
endif
end subroutine ncd_iolocal_real_2d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_gs_real1d
!
! !INTERFACE:
subroutine ncd_iolocal_gs_real1d(ncid, varname, flag, data, clmlevel, start, count, status, missing, usepio) 3,20
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial real field out to netCDF file
!
! !USES:
use spmdGathScatMod
, only : scatter_data_from_master, gather_data_to_master
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! input unit
character(len=*) ,intent(in) :: varname ! variable name
character(len=*) ,intent(in) :: flag ! 'read' or 'write'
real(r8),pointer :: data(:) ! local decomposition input data (out)
character(len=*) ,intent(in) :: clmlevel ! type of grid
integer, optional,intent(in) :: start(:) ! netcdf start index
integer, optional,intent(in) :: count(:) ! netcdf count index
integer, optional,intent(out) :: status ! return code
real(r8),optional,intent(in) :: missing ! missing value
logical, optional,intent(in) :: usepio ! use pio lib
!--- rcodes:
! 0 : success
! -99 : general error
! -5 : var not found on read
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n
real(r8), pointer :: arrayg(:)
integer :: gsize ! array global size from gsmap
integer :: lstart(4),lcount(4) ! local start/count arrays
integer :: varid ! varid
integer :: ndims ! ndims for var
integer :: dids(4) ! dim ids
character(len=32) :: dname(4) ! dim names
integer :: dlen(4) ! dim lens
#if (defined BUILDPIO)
type(pio_vardesc_plus_type),pointer :: pio_vardesc_plus
type(pio_iodesc_plus_type) ,pointer :: pio_iodesc_plus
integer :: vdnum ! vardesc num in list
integer :: basetype ! pio initdecomp info
integer :: lenblocks ! pio initdecomp info
integer :: dims(4) ! pio initdecomp info
integer :: iodnum ! iodesc num in list
integer,pointer :: compDOF(:)
integer,pointer :: ioDOF(:)
integer(pio_offset),pointer :: pstart(:),pcount(:)
real(r8),pointer :: data1d(:) ! 1d copy of data starting at index 1
integer :: n1,n1b,n1e,n1s
#endif
logical :: varpresent ! if true, variable is on tape
integer :: rcode ! local return code
integer :: ier ! error code
integer :: data_offset ! offset to single grid point for column model
integer :: ndata ! count of pft's or columns to read
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_iolocal_gs_real1d' ! subroutine name
!-----------------------------------------------------------------------
call t_startf('ncd_lgs1d_total')
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),' ',trim(clmlevel),lusepio
endif
rcode = 0
lstart = 1
lcount = 1
if (present(start).and.present(count)) then
lstart(1:size(start)) = start(1:size(start))
lcount(1:size(count)) = count(1:size(count))
endif
gsize = get_clmlevel_gsize
(clmlevel)
if (flag == 'read') then
if (masterproc) then
allocate(arrayg(gsize))
call check_var
(ncid, varname, varid, varpresent)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,clmlevel,lstart,lcount)
call check_ret
(nf_get_vara_double(ncid, varid, lstart, lcount, arrayg), subname)
else
if (present(start).and.present(count)) then
call check_ret
(nf_get_vara_double(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_get_var_double(ncid, varid, arrayg), subname)
endif
endif
else
rcode = -5
endif
endif
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if ( varpresent ) call scatter_data_from_master
(data,arrayg,clmlevel)
if (masterproc) then
deallocate(arrayg)
endif
elseif (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call t_startf('ncd_lgs1d_wptotal')
call ncd_inqvdesc
(varname,vdnum,subname,usepio=lusepio)
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
pio_vardesc_plus => pio_vardesc_list(vdnum)
iodnum = pio_vardesc_plus%iodnum
if (iodnum < 1 .or. iodnum > pio_num_iodesc) then
write(iulog,*) trim(subname),' ERROR in iodnum from vardesc ',trim(varname),iodnum
call endrun
()
endif
pio_iodesc_plus => pio_iodesc_list(iodnum)
!------------------------
!--- setup iodesc if it's not set yet ---
!------------------------
if (.not. pio_iodesc_plus%set) then
call t_startf('ncd_lgs1d_wpsetdof')
baseTYPE = MPI_REAL8
dims(:) = 1
ndims = pio_iodesc_plus%ndims
do n = 1,ndims
call ncd_inqdlen
(ncid,pio_iodesc_plus%dimids(n),dims(n),trim(subname),usepio=lusepio)
if (dims(n) == 0) dims(n) = 1 ! sometimes for time axis?
enddo
lenBLOCKS = 1
call ncd_setDOF
(clmlevel,dims,compDOF,ioDOF,pstart,pcount)
!--- pio call ---
if (ncd_pio_UseBoxRearr) then
call pio_initDecomp(pio_File,baseTYPE,dims,compDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
else
call pio_initDecomp(pio_File,baseTYPE,dims,lenBLOCKS,compDOF,ioDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
endif
deallocate(compDOF)
deallocate(IODOF)
deallocate(pstart)
deallocate(pcount)
pio_iodesc_plus%set = .true.
call t_stopf('ncd_lgs1d_wpsetdof')
endif
!------------------------
!--- end setup iodesc ---
!------------------------
call pio_setVarDesc(pio_iodesc_plus%pio_iodesc,pio_vardesc_plus%pio_vardesc)
!--- copy data to 1d array ---
call t_startf('ncd_lgs1d_wpcopy')
n1b = lbound(data,dim=1)
n1e = ubound(data,dim=1)
n1s = size(data,dim=1)
allocate(data1d(n1s),stat=n)
call shr_sys_flush
(iulog)
n = 0
do n1 = n1b,n1e
n = n + 1
data1d(n) = data(n1)
enddo
call t_stopf('ncd_lgs1d_wpcopy')
call t_startf('ncd_lgs1d_wpwrit')
call PIO_write_darray(pio_File,pio_vardesc_plus%pio_varDesc,data1d,ier)
call t_stopf('ncd_lgs1d_wpwrit')
deallocate(data1d)
call t_stopf('ncd_lgs1d_wptotal')
#endif
else
call t_startf('ncd_lgs1d_wtotal')
if (masterproc) then
allocate(arrayg(gsize))
endif
call t_startf('ncd_lgs1d_wgath')
if (present(missing)) then
call gather_data_to_master
(data,arrayg,clmlevel,missing)
else
call gather_data_to_master
(data,arrayg,clmlevel)
endif
call t_stopf('ncd_lgs1d_wgath')
if (masterproc) then
call check_ret
(nf_inq_varid(ncid, varname, varid), subname)
call t_startf('ncd_lgs1d_wwrit')
if (present(start).and.present(count)) then
call check_ret
(nf_put_vara_double(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_put_var_double(ncid, varid, arrayg), subname)
endif
call t_stopf('ncd_lgs1d_wwrit')
deallocate(arrayg)
endif
call t_stopf('ncd_lgs1d_wtotal')
endif
else
if (masterproc) then
write(iulog,*) subname,' error: unsupported flag ',trim(flag)
call endrun
()
endif
endif
if (present(status)) then
call mpi_bcast(rcode, 1, MPI_INTEGER, 0, mpicom, ier)
status = rcode
endif
call t_stopf('ncd_lgs1d_total')
end subroutine ncd_iolocal_gs_real1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_iolocal_gs_real2d
!
! !INTERFACE:
subroutine ncd_iolocal_gs_real2d(ncid, varname, flag, data, clmlevel, start, count, status, missing, usepio) 2,19
!
! !DESCRIPTION:
! Netcdf i/o of 2d initial real field out to netCDF file
!
! !USES:
use spmdGathScatMod
, only : scatter_data_from_master, gather_data_to_master
!
! !ARGUMENTS:
implicit none
integer ,intent(in) :: ncid ! input unit
character(len=*) ,intent(in) :: varname ! variable name
character(len=*) ,intent(in) :: flag ! 'read' or 'write'
real(r8),pointer :: data(:,:) ! local decomposition input data (out)
character(len=*) ,intent(in) :: clmlevel ! type of grid
integer, optional,intent(in) :: start(:) ! netcdf start index
integer, optional,intent(in) :: count(:) ! netcdf count index
integer, optional,intent(out) :: status ! return code
real(r8),optional,intent(in) :: missing ! missing value
logical, optional,intent(in) :: usepio ! use pio lib
!--- rcodes:
! 0 : success
! -99 : general error
! -5 : var not found on read
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer :: n
real(r8), pointer :: arrayg(:,:)
integer :: gsize ! array global size from gsmap
integer :: ksize ! level ndims
integer :: lstart(4),lcount(4) ! local start/count arrays
logical :: varpresent ! if true, variable is on tape
integer :: varid ! varid
integer :: dids(4) ! dim ids
character(len=32) :: dname(4) ! dim names
integer :: dlen(4) ! dim lens
#if (defined BUILDPIO)
type(pio_vardesc_plus_type),pointer :: pio_vardesc_plus
type(pio_iodesc_plus_type) ,pointer :: pio_iodesc_plus
integer :: vdnum ! vardesc num in list
integer :: basetype ! pio initdecomp info
integer :: lenblocks ! pio initdecomp info
integer :: dims(4) ! pio initdecomp info
integer :: iodnum ! iodesc num in list
integer,pointer :: compDOF(:)
integer,pointer :: ioDOF(:)
integer(pio_offset),pointer :: pstart(:),pcount(:)
real(r8),pointer :: data1d(:) ! 1d copy of data starting at index 1
integer :: n1,n2,n1b,n1e,n1s,n2b,n2e,n2s
#endif
integer :: rcode ! local return code
integer :: ier ! error code
integer :: data_offset ! offset to single grid point for column model
integer :: ndata ! count of pft's or columns to read
logical :: lusepio ! local usepio variable
character(len=*),parameter :: subname='ncd_iolocal_gs_real2d' ! subroutine name
!-----------------------------------------------------------------------
call t_startf('ncd_lgs2d_total')
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(flag),' ',trim(varname),' ',trim(clmlevel),lusepio
endif
rcode = 0
lstart = 1
lcount = 1
if (present(start).and.present(count)) then
lstart(1:size(start)) = start(1:size(start))
lcount(1:size(count)) = count(1:size(count))
endif
gsize = get_clmlevel_gsize
(clmlevel)
ksize = size(data,dim=2)
if (flag == 'read') then
if (masterproc) then
allocate(arrayg(gsize,ksize))
call check_var
(ncid, varname, varid, varpresent)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,clmlevel,lstart,lcount)
call check_ret
(nf_get_vara_double(ncid, varid, lstart, lcount, arrayg), subname)
else
if (present(start).and.present(count)) then
call check_ret
(nf_get_vara_double(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_get_var_double(ncid, varid, arrayg), subname)
endif
endif
else
rcode = -5
endif
endif
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if ( varpresent ) call scatter_data_from_master
(data,arrayg,clmlevel)
if (masterproc) then
deallocate(arrayg)
endif
elseif (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call t_startf('ncd_lgs2d_wptotal')
call ncd_inqvdesc
(varname,vdnum,subname,usepio=lusepio)
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
pio_vardesc_plus => pio_vardesc_list(vdnum)
iodnum = pio_vardesc_plus%iodnum
if (iodnum < 1 .or. iodnum > pio_num_iodesc) then
write(iulog,*) trim(subname),' ERROR in iodnum from vardesc ',trim(varname),iodnum
call endrun
()
endif
pio_iodesc_plus => pio_iodesc_list(iodnum)
!------------------------
!--- setup iodesc if it's not set yet ---
!------------------------
if (.not. pio_iodesc_plus%set) then
call t_startf('ncd_lgs2d_wpsetdof')
baseTYPE = MPI_REAL8
dims(:) = 1
ndims = pio_iodesc_plus%ndims
do n = 1,ndims
call ncd_inqdlen
(ncid,pio_iodesc_plus%dimids(n),dims(n),trim(subname),usepio=lusepio)
if (dims(n) == 0) dims(n) = 1 ! sometimes for time axis?
enddo
lenBLOCKS = 1
call ncd_setDOF
(clmlevel,dims,compDOF,ioDOF,pstart,pcount)
!--- pio call ---
if (ncd_pio_UseBoxRearr) then
call pio_initDecomp(pio_File,baseTYPE,dims,compDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
else
call pio_initDecomp(pio_File,baseTYPE,dims,lenBLOCKS,compDOF,ioDOF,pstart,pcount,pio_iodesc_plus%pio_ioDesc)
endif
deallocate(compDOF)
deallocate(IODOF)
deallocate(pstart)
deallocate(pcount)
pio_iodesc_plus%set = .true.
call t_stopf('ncd_lgs2d_wpsetdof')
endif
!------------------------
!--- end setup iodesc ---
!------------------------
call pio_setVarDesc(pio_iodesc_plus%pio_iodesc,pio_vardesc_plus%pio_vardesc)
call t_startf('ncd_lgs2d_wpcopy')
n1b = lbound(data,dim=1)
n1e = ubound(data,dim=1)
n1s = size (data,dim=1)
n2b = lbound(data,dim=2)
n2e = ubound(data,dim=2)
n2s = size (data,dim=2)
allocate(data1d(n1s*n2s),stat=n)
n = 0
do n2 = n2b,n2e
do n1 = n1b,n1e
n = n + 1
data1d(n) = data(n1,n2)
enddo
enddo
call t_stopf('ncd_lgs2d_wpcopy')
call t_startf('ncd_lgs2d_wpwrit')
call PIO_write_darray(pio_File,pio_vardesc_plus%pio_varDesc,data1d,ier)
call t_stopf('ncd_lgs2d_wpwrit')
deallocate(data1d)
call t_stopf('ncd_lgs2d_wptotal')
#endif
else
call t_startf('ncd_lgs2d_wtotal')
if (masterproc) then
allocate(arrayg(gsize,ksize))
endif
call t_startf('ncd_lgs2d_wgath')
if (present(missing)) then
call gather_data_to_master
(data,arrayg,clmlevel,missing)
else
call gather_data_to_master
(data,arrayg,clmlevel)
endif
call t_stopf('ncd_lgs2d_wgath')
if (masterproc) then
call check_ret
(nf_inq_varid(ncid, varname, varid), subname)
call t_startf('ncd_lgs2d_wwrit')
if (present(start).and.present(count)) then
call check_ret
(nf_put_vara_double(ncid, varid, start, count, arrayg), subname)
else
call check_ret
(nf_put_var_double(ncid, varid, arrayg), subname)
endif
call t_stopf('ncd_lgs2d_wwrit')
deallocate(arrayg)
endif
call t_stopf('ncd_lgs2d_wtotal')
endif
else
if (masterproc) then
write(iulog,*) subname,' error: unsupported flag ',trim(flag)
call endrun
()
endif
endif
if (present(status)) then
call mpi_bcast(rcode, 1, MPI_INTEGER, 0, mpicom, ier)
status = rcode
endif
call t_stopf('ncd_lgs2d_total')
end subroutine ncd_iolocal_gs_real2d
!------------------------------------------------------------------------
!***** end include ncdio_local_subs.inc *****
!------------------------------------------------------------------------
!-----------------------------------------------------------------------
!***** begin include ncdio_global_subs.inc *****
! this next section has been autogenerated from
! --- gen_ncdio_global_subs.csh ---
! and manually included. this section ends at "end include ..."
!-----------------------------------------------------------------------
! #include <ncdio_global_subs.inc>
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_int_var
!
! !INTERFACE:
subroutine ncd_ioglobal_int_var(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global var int array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(inout) :: data ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 0 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_int_var'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = 1
allocate(piodata(n))
piodata(1) = data
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = 1
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_int(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_int(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_int(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, 1, MPI_INTEGER, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_int_var
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_real_var
!
! !INTERFACE:
subroutine ncd_ioglobal_real_var(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global var real array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , intent(inout) :: data ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
real(r8) ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 0 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_real_var'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = 1
allocate(piodata(n))
piodata(1) = data
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = 1
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_double(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_double(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_double(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, 1, MPI_REAL8, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_real_var
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_int_1d
!
! !INTERFACE:
subroutine ncd_ioglobal_int_1d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 1d int array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(inout) :: data (:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 1 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_int_1d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
piodata = data
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_int(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_int(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_int(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_INTEGER, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_int_1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_real_1d
!
! !INTERFACE:
subroutine ncd_ioglobal_real_1d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 1d real array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , intent(inout) :: data (:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
real(r8) ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 1 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_real_1d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
piodata = data
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_double(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_double(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_double(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_REAL8, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_real_1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_char_1d
!
! !INTERFACE:
subroutine ncd_ioglobal_char_1d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 1d char array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
character(len=*), intent(inout) :: data ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
character,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 1 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_char_1d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = len(data)
allocate(piodata(n))
do n1 = 1,n
piodata(n1) = data(n1:n1)
enddo
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = len(data)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_text(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_text(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_text(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, len(data), MPI_CHARACTER, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_char_1d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_int_2d
!
! !INTERFACE:
subroutine ncd_ioglobal_int_2d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 2d int array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(inout) :: data (:,:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 2 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_int_2d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
n = 0
do n2 = 1, size(data,dim=2)
do n1 = 1, size(data,dim=1)
n = n + 1
piodata(n) = data(n1,n2)
enddo
enddo
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_int(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_int(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_int(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_INTEGER, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_int_2d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_real_2d
!
! !INTERFACE:
subroutine ncd_ioglobal_real_2d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 2d real array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , intent(inout) :: data (:,:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
real(r8) ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 2 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_real_2d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
n = 0
do n2 = 1, size(data,dim=2)
do n1 = 1, size(data,dim=1)
n = n + 1
piodata(n) = data(n1,n2)
enddo
enddo
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_double(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_double(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_double(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_REAL8, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_real_2d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_int_3d
!
! !INTERFACE:
subroutine ncd_ioglobal_int_3d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 3d int array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
integer , intent(inout) :: data (:,:,:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
integer ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 3 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_int_3d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
n = 0
do n3 = 1, size(data,dim=3)
do n2 = 1, size(data,dim=2)
do n1 = 1, size(data,dim=1)
n = n + 1
piodata(n) = data(n1,n2,n3)
enddo
enddo
enddo
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_int(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_int(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_int(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_INTEGER, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_int_3d
!-----------------------------------------------------------------------
!BOP
!
! !IROUTINE: ncd_ioglobal_real_3d
!
! !INTERFACE:
subroutine ncd_ioglobal_real_3d(varname, data, flag, ncid, readvar, nt, bcast, usepio) 1,25
!
! !DESCRIPTION:
! netcdf I/O of global 3d real array
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: flag ! 'read' or 'write'
integer , intent(in) :: ncid ! input unit
character(len=*), intent(in) :: varname ! variable name
real(r8) , intent(inout) :: data (:,:,:) ! raw data
logical , optional, intent(out):: readvar ! was var read?
integer , optional, intent(in) :: nt ! time sample index
logical , optional, intent(in) :: bcast ! bcast on read?
logical , optional, intent(in) :: usepio ! use pio lib
!
! !REVISION HISTORY:
!
!
! !LOCAL VARIABLES:
!EOP
real(r8) ,pointer :: piodata(:) ! copy of data in 1d
integer :: n,n1,n2,n3 ! local counter
integer :: varid ! netCDF variable id
integer :: vdnum ! vardesc number
#if (defined BUILDPIO)
type(var_desc_t),pointer :: pio_vardesc ! local vardesc pointer
#endif
integer :: ier ! error code
integer :: start(4), count(4) ! output bounds
integer :: nd,did(4),ld(4) ! var/dim error checking
character(len=32) :: vname ! variable error checking
character(len=32) :: dname ! dimension error checking
logical :: varpresent ! if true, variable is on tape
logical :: lbcast ! local copy of bcast flag
logical :: lusepio ! local usepio variable
integer,parameter :: ndims = 3 ! data dims
character(len=*),parameter :: subname='ncd_ioglobal_real_3d'
!-----------------------------------------------------------------------
lusepio = ncd_pio_def
if (present(usepio)) then
lusepio = usepio
endif
if (masterproc .and. debug > 1) then
write(iulog,*) trim(subname),' ',trim(varname),lusepio
endif
if (lusepio) then
n = size(data)
allocate(piodata(n))
n = 0
do n3 = 1, size(data,dim=3)
do n2 = 1, size(data,dim=2)
do n1 = 1, size(data,dim=1)
n = n + 1
piodata(n) = data(n1,n2,n3)
enddo
enddo
enddo
endif
start = 1
count = 1
lbcast = lbcast_def
if (present(bcast)) then
lbcast = bcast
endif
if (flag == 'write') then
if (lusepio) then
#if (defined BUILDPIO)
call ncd_inqvdesc
(varname, vdnum, subname, usepio=lusepio)
pio_vardesc => pio_vardesc_list(vdnum)%pio_varDesc
if (vdnum < 1 .or. vdnum > pio_num_vardesc) then
write(iulog,*) trim(subname),' ERROR in vdnum from inqvdesc ',trim(varname),vdnum
call endrun
()
endif
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio, pio_varDesc=pio_varDesc)
#endif
else
call ncd_inqvid
(ncid, varname, varid, subname, usepio=lusepio)
call ncd_inqvname
(ncid, varid, vname, subname, usepio=lusepio)
call ncd_inqvdims
(ncid, varid, nd, subname, usepio=lusepio)
call ncd_inqvdids
(ncid, varid, did, subname, usepio=lusepio)
endif
if (masterproc .and. (trim(varname) /= trim(vname))) then
write(iulog,*) trim(subname),' ERROR: varnames do not match ',trim(varname),' ',trim(vname)
call endrun
()
endif
if (masterproc .and. (nd - ndims > 1 .or. nd - ndims < 0)) then
write(iulog,*) trim(subname),' ERROR: array ndims ne cdf var ndims ',trim(varname),ndims,nd
call endrun
()
endif
do n = 1, ndims
call ncd_inqdlen
(ncid, did(n), ld(n), subname, usepio=lusepio)
call ncd_inqdname
(ncid, did(n), dname, subname, usepio=lusepio)
count(n) = size(data,dim=n)
if (masterproc .and. count(n) /= ld(n)) then
write(iulog,*) trim(subname),' ERROR: array size ne cdf var size ',trim(varname),n,trim(dname),count(n),ld(n)
call endrun
()
endif
enddo
if (present(nt)) then
start(ndims+1) = nt
endif
if (lusepio) then
#if (defined BUILDPIO)
call check_ret_pio
(PIO_put_var(pio_file, varid, start, count, piodata), subname)
#endif
else
if (masterproc) call check_ret
(nf_put_vara_double(ncid, varid, start, count, data), subname)
endif
else if (flag == 'read') then
call ncd_inqvid
(ncid, varname, varid, subname, readvar=varpresent, usepio=lusepio)
if (varpresent) then
if (single_column) then
call scam_field_offsets
(ncid,'undefined',start,count)
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, start, count, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_vara_double(ncid, varid, start, count, data), subname)
endif
else
if (lusepio) then
#if (defined BUILDPIO)
! call check_ret_pio(PIO_get_var(ncid, varid, piodata), subname)
if (masterproc) write(iulog,*) trim(subname),' pio not implemented'
call endrun
()
#endif
else
if (masterproc) call check_ret
(nf_get_var_double(ncid, varid, data), subname)
endif
endif
endif
if (lbcast) then
call mpi_bcast(varpresent, 1, MPI_LOGICAL, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for varpresent'
call endrun
()
endif
if (varpresent) then
call mpi_bcast(data, size(data), MPI_REAL8, 0, mpicom, ier)
if (ier /= 0) then
write(iulog,*) trim(subname), &
' ERROR from mpi_bcast for data'
call endrun
()
endif
endif
endif
if (present(readvar)) readvar = varpresent
endif ! flag
if (lusepio) then
deallocate(piodata)
endif
end subroutine ncd_ioglobal_real_3d
!------------------------------------------------------------------------
!***** end include ncdio_global_subs.inc *****
!------------------------------------------------------------------------
#if (defined BUILDPIO)
!BOP
!
! !IROUTINE: subroutine ncd_setDOF
!
! !INTERFACE:
!------------------------------------------------------------------------
subroutine ncd_setDOF(clmlevel,dims,compDOF,ioDOF,start,count) 4,6
!
! !DESCRIPTION:
! Setup DOF and start/count arrays for pio
!
! !USES:
use decompMod
, only : get_clmlevel_gsize,get_clmlevel_dsize
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: clmlevel ! dimension 1 name
integer , intent(in) :: dims(:)
integer,pointer , intent(inout) :: compDOF(:)
integer,pointer , intent(inout) :: ioDOF(:)
integer(pio_offset),pointer , intent(inout) :: start(:)
integer(pio_offset),pointer , intent(inout) :: count(:)
!
! !REVISION HISTORY:
! Created by T Craig, Aug 2007
!
! !LOCAL VARIABLES:
!EOP
integer :: m,n,cnt,n1,n2,n3,n4,n1s,n2s,n3s,n4s
integer :: ndims ! size of dims
integer :: gsize ! global size of clmlevel
integer :: gsmap_lsize ! local size of gsmap
integer :: gsmap_gsize ! global size of gsmap
integer :: fullsize ! size of entire array on cdf
integer :: vsize ! other dimensions
integer :: iosize ! local iodof size
integer :: ier ! error status
logical :: found ! found flag
type(mct_gsMap),pointer :: gsmap ! global seg map
integer, pointer,dimension(:) :: gsmOP ! gsmap ordered points
character(len=32) :: subname = 'ncd_setDOF'
!-----------------------------------------------
call get_clmlevel_gsmap
(clmlevel,gsmap)
ndims = size(dims)
gsize = get_clmlevel_gsize
(clmlevel)
gsmap_lsize = mct_gsmap_lsize(gsmap,mpicom)
gsmap_gsize = mct_gsmap_gsize(gsmap)
fullsize = 1
do n = 1,ndims
fullsize = fullsize*dims(n)
enddo
vsize = fullsize / gsize
if (mod(fullsize,gsize) /= 0) then
write(iulog,*) subname,' ERROR in vsize ',fullsize,gsize,vsize
call endrun
()
endif
allocate(start(4),count(4))
start = 1
count = 1
count(1:ndims) = dims(1:ndims)
if (ncd_pio_IODOF_rootonly) then
if (iam /= 0) then
count = 0
endif
else
found = .false.
do n = ndims,1,-1
if (.not.found .and. dims(n) >= pio_num_iotasks) then
found = .true.
if (pio_IOproc) then
count(n) = dims(n) / pio_num_iotasks
start(n) = pio_io_rank*count(n) + 1
m = mod(dims(n),pio_num_iotasks)
start(n) = start(n) + min(pio_io_rank,m)
if (pio_io_rank < m) count(n) = count(n) + 1
else
count = 0
endif
endif
enddo
if (.not.found) then
write(iulog,*) trim(subname),' ERROR: start,count not computed for num_iotasks = ', &
pio_num_iotasks,' and dims = ',dims
call endrun
()
endif
endif
iosize = 1
do n = 1,ndims
iosize = iosize*count(n)
enddo
allocate(compDOF(gsmap_lsize*vsize))
allocate(ioDOF(iosize))
call mct_gsmap_OP(gsmap,iam,gsmOP)
cnt = 0
do n = 1,vsize
do m = 1,gsmap_lsize
cnt = cnt + 1
compDOF(cnt) = (n-1)*gsmap_gsize + gsmOP(m)
enddo
enddo
cnt = 0
do n4 = start(4),start(4)+count(4)-1
n4s = (n4-1)*dims(3)*dims(2)*dims(1)
do n3 = start(3),start(3)+count(3)-1
n3s = n4s + (n3-1)*dims(2)*dims(1)
do n2 = start(2),start(2)+count(2)-1
n2s = n3s + (n2-1)*dims(1)
do n1 = start(1),start(1)+count(1)-1
n1s = n2s + (n1)
cnt = cnt + 1
ioDOF(cnt) = n1s
enddo
enddo
enddo
enddo
if (debug > 1) then
do m = 0,npes-1
if (iam == m) then
write(iulog,*) trim(subname),' sizes1 = ',iam,gsize,gsmap_gsize,gsmap_lsize
write(iulog,*) trim(subname),' sizes2 = ',iam,fullsize,npes,vsize,iosize
write(iulog,*) trim(subname),' dims = ',iam,(start(n),count(n),dims(n),n=1,4)
write(iulog,*) trim(subname),' compDOF = ',iam,size(compDOF),minval(compDOF),maxval(compDOF)
write(iulog,*) trim(subname),' ioDOF = ',iam,size(ioDOF),minval(ioDOF),maxval(ioDOF)
call shr_sys_flush
(iulog)
endif
call mpi_barrier(mpicom,ier)
enddo
endif
deallocate(gsmOP)
end subroutine ncd_setDOF
#endif
!------------------------------------------------------------------------
!BOP
!
! !IROUTINE: subroutine scam_field_offsets
!
! !INTERFACE:
subroutine scam_field_offsets(ncid,dim1name,start,count) 13,18
!
! !DESCRIPTION:
! Read/Write initial data from/to netCDF instantaneous initial data file
!
! !USES:
use clm_varpar
, only : maxpatch
use nanMod
, only : nan
use clm_varctl
, only : scmlon,scmlat,single_column
!
! !ARGUMENTS:
implicit none
character(len=*), intent(in) :: dim1name ! dimension 1 name
integer, intent(in) :: ncid ! netCDF dataset id
integer, intent(inout) :: start(:) ! start index
integer, intent(inout) :: count(:) ! count to retrieve
!
! !CALLED FROM: subroutine inicfields
!
! !REVISION HISTORY:
! Created by John Truesdale
!
! !LOCAL VARIABLES:
!EOP
integer :: data_offset ! offset into land array 1st column
integer :: ndata ! number of column (or pft points to read)
real(r8) , pointer :: cols1dlon(:) ! holds cols1d_ixy var
real(r8) , pointer :: cols1dlat(:) ! holds cols1d_jxy var
real(r8) , pointer :: pfts1dlon(:) ! holds pfts1d_ixy var
real(r8) , pointer :: pfts1dlat(:) ! holds pfts1d_jxy var
integer :: cols(maxpatch) ! grid cell columns for scam
integer :: pfts(maxpatch) ! grid cell pfts for scam
integer :: cc,i ! index variable
integer :: totpfts ! total number of pfts
integer :: totcols ! total number of columns
integer :: dimid ! netCDF dimension id
integer :: varid ! netCDF variable id
integer :: ret ! return code
integer :: latidx,lonidx ! latitude/longitude indices
real(r8):: closelat,closelon ! closest latitude and longitude indices
character(len=32) :: subname = 'scam_field_offsets'
!------------------------------------------------------------------------
! find closest land grid cell for this point
call scam_setlatlonidx
(ncid,scmlat,scmlon,closelat,closelon,latidx,lonidx)
if (dim1name == 'column') then
call check_ret
(nf_inq_dimid (ncid, 'column', dimid), subname)
call check_ret
(nf_inq_dimlen (ncid, dimid, totcols), subname)
allocate (cols1dlon(totcols))
allocate (cols1dlat(totcols))
call check_ret
(nf_inq_varid (ncid, 'cols1d_lon', varid), subname)
call check_ret
(nf_get_var_double (ncid, varid, cols1dlon), subname)
call check_ret
(nf_inq_varid (ncid, 'cols1d_lat', varid), subname)
call check_ret
(nf_get_var_double (ncid, varid, cols1dlat), subname)
cols(:) = nan
data_offset = nan
i = 1
ndata = 0
do cc = 1, totcols
if (cols1dlon(cc) == closelon.and.cols1dlat(cc) == closelat) then
cols(i)=cc
ndata =i
i=i+1
end if
end do
if (ndata == 0) then
write(iulog,*)'couldnt find any columns for this latitude ',latidx,' and longitude ',lonidx
call endrun
else
data_offset=cols(1)
end if
deallocate (cols1dlon)
deallocate (cols1dlat)
start(1) = data_offset
count(1) = ndata
else if (dim1name == 'pft') then
call check_ret
(nf_inq_dimid (ncid, 'pft', dimid), subname)
call check_ret
(nf_inq_dimlen (ncid, dimid, totpfts), subname)
allocate (pfts1dlon(totpfts))
allocate (pfts1dlat(totpfts))
call check_ret
( nf_inq_varid (ncid, 'pfts1d_lon', varid), subname)
call check_ret
(nf_get_var_double (ncid, varid, pfts1dlon), subname)
call check_ret
( nf_inq_varid (ncid, 'pfts1d_lat', varid), subname)
call check_ret
(nf_get_var_double (ncid, varid, pfts1dlat), subname)
pfts(:) = nan
data_offset = nan
i = 1
ndata = 0
do cc = 1, totpfts
if (pfts1dlon(cc) == closelon.and.pfts1dlat(cc) == closelat) then
pfts(i)=cc
ndata =i
i=i+1
end if
end do
if (ndata == 0) then
write(iulog,*)'couldnt find any pfts for this latitude ',closelat,' and longitude ',closelon
call endrun
else
data_offset=pfts(1)
end if
deallocate (pfts1dlon)
deallocate (pfts1dlat)
start(1) = data_offset
count(1) = ndata
else
start(1) = lonidx
count(1) = 1
start(2) = latidx
count(2) = 1
write(iulog,*) trim(subname),' scam_setlatlonidx ',lonidx,latidx
endif
end subroutine scam_field_offsets
!------------------------------------------------------------------------
end module ncdio