00001 !
00002 ! $Id: compute_starts_counts.h,v 1.1 2005/09/14 13:35:28 pmarches Exp $
00003 !
00004 ! Auxiliary module "compute_starts_counts.h":
00005 !-------------------------------------------------------
00006 !Given two input variables, "type" and "record", which specify grid
00007 !type of the field to be read/written from/to netCDF file, and record
00008 !number (if there is an unlimited dimension for that field in the
00009 !netCDF file), compute "start" and "count" arrays which contain
00010 !starting indices and proper counts corresponding to the field data
00011 !stored in the file.
00012 !
00013 ! This module supports three different policies of reading/writing
00014 !the data: (1) in the case of shared memory code the data is always
00015 !written by single CPU into a single file, so that start/count are
00016 !basically determined by the dimensions of arrays as it is written
00017 !in the file; (2) in the case of MPI code the data can still be
00018 !written into a single file, or (3) multiple files containing data
00019 !individually for each MPI-node (this option is activated by
00020 !CPP-switch PARALLEL_FILES); In the case of MPI-single-file mode each
00021 !MPI-node (one at-a-time) writes a rectangular block of array, so that
00022 !"starts" depend on the position of node ii,jj on the processor grid,
00023 !while "counts" corresponds to the size of MPI subdomains. In the
00024 !case of PARALLEL_FILES "starts" corresponding to horizontal
00025 !dimensions are both equal to 1, "counts" correspond to subdomains
00026 !with physical boundaries kept, but MPI-halos striped out.
00027 !
00028 ! Additionally, this module computes ranges "imin,imax,jmin,jmax"
00029 !which define starting/ending indices of the portion of model array
00030 !to be written into the file [hence in all cases count(1)=imax-imin+1,
00031 !and count(2)=jmax-jmin+1]. This is necessary because model arrays
00032 !have slightly different shapes than the corresponding arrays in the
00033 !netCDF files. The differences are due to index shifting (netCDF
00034 !array index must always start from 1, while Fortran does not);
00035 !Fortran array dimension padding; and stripping periodic/computational
00036 !margins.
00037
00038 integer imin,imax,jmin,jmax, start(4), count(4),
00039 & vert_type, horiz_type
00040
00041 ierr=0 ! These are default settings. In all cases
00042 do i=1,4 ! start,count(1:2) correspond to XI- and
00043 start(i)=1 ! ETA-dimensions, while index 3 is for either
00044 count(i)=1 ! vertical dimension (if any) or time record
00045 enddo ! (2D-fields); 4 is for time record only
00046
00047 vert_type=type/4 ! Decode grid type into vertical
00048 horiz_type=type-4*vert_type ! and horizontal grid types, then
00049 jmin=horiz_type/2 ! calculate starting indices in
00050 imin=horiz_type-2*jmin ! horizontal directions.
00051
00052 #ifdef MPI
00053 # ifdef PARALLEL_FILES
00054 # ifdef EW_PERIODIC
00055 imin=1
00056 imax=Lm
00057 # else
00058 if (ii.gt.0) imin=1
00059 if (ii.eq.NP_XI-1) then
00060 imax=Lm+1
00061 else
00062 imax=Lm
00063 endif
00064 # endif
00065 # ifdef NS_PERIODIC
00066 jmin=1
00067 jmax=Mm
00068 # else
00069 if (jj.gt.0) jmin=1
00070 if (jj.eq.NP_ETA-1) then
00071 jmax=Mm+1
00072 else
00073 jmax=Mm
00074 endif
00075 # endif
00076 # else
00077 if (ii.gt.0) then
00078 start(1)=2-imin+ii*Lm
00079 imin=1
00080 endif
00081 if (ii.eq.NP_XI-1) then
00082 imax=Lm+1
00083 else
00084 imax=Lm
00085 endif
00086 if (jj.gt.0) then
00087 start(2)=2-jmin+jj*Mm
00088 jmin=1
00089 endif
00090 if (jj.eq.NP_ETA-1) then
00091 jmax=Mm+1
00092 else
00093 jmax=Mm
00094 endif
00095 # endif
00096 #else
00097 imax=Lm+1
00098 jmax=Mm+1
00099 #endif
00100 count(1)=imax-imin+1
00101 count(2)=jmax-jmin+1
00102
00103 c** write(stdout,'(1x,A,i4,1x,A,i2,2(3x,A,I2,2x,A,I3,2x,A,I3))')
00104 c** & 'NF_READ/WRITE: mynode=',mynode,'horiz_grid',horiz_type,
00105 c** & 'ii=',ii, 'imin=',imin, 'imax=',imax,
00106 C** & 'jj=',jj, 'jmin=',jmin, 'jmax=',jmax
00107
00108 if (vert_type.eq.0) then ! Sort out vertical grids:
00109 start(3)=record !<-- 2D field variables
00110 elseif (vert_type.eq.1) then
00111 count(3)=N !<-- 3D RHO-grid
00112 start(4)=record
00113 elseif (vert_type.eq.2) then
00114 count(3)=N+1 !<-- 3D W-grid
00115 start(4)=record
00116 else
00117 ierr=ierr+1
00118 endif