From ddaac8a567d0799c195e2aef36d59ae3bcb18dec Mon Sep 17 00:00:00 2001 From: Philippe WAUTELET <philippe.wautelet@aero.obs-mip.fr> Date: Tue, 27 Jun 2017 16:50:17 +0200 Subject: [PATCH] Philippe 27/06/2017: IO: * added IO_BCAST_FIELD_METADATA subroutine * added IO_READ_CHECK_FIELD_ATTR_NC4 subroutine * do not use FMHEADER anymore for IO_READ_FIELD and its subroutines * treat error messages as soon as possible --- src/LIB/SURCOUCHE/src/fmread_ll.f90 | 53 ++++--- src/LIB/SURCOUCHE/src/fmreadwrit.f90 | 93 ++++++++----- src/LIB/SURCOUCHE/src/mode_io.f90 | 4 +- src/LIB/SURCOUCHE/src/mode_netcdf.f90 | 192 ++++++++++++++++++++++++-- 4 files changed, 278 insertions(+), 64 deletions(-) diff --git a/src/LIB/SURCOUCHE/src/fmread_ll.f90 b/src/LIB/SURCOUCHE/src/fmread_ll.f90 index cae9e5e85..f7b6a1d87 100644 --- a/src/LIB/SURCOUCHE/src/fmread_ll.f90 +++ b/src/LIB/SURCOUCHE/src/fmread_ll.f90 @@ -34,6 +34,7 @@ USE MODE_FIELD USE MODE_NETCDF #endif USE MODE_MSG +USE MODE_READWRITE_LFI IMPLICIT NONE @@ -104,8 +105,8 @@ END SUBROUTINE FM_READ_ERR SUBROUTINE BCAST_HEADER(TPFD,TPFMH) USE MODE_FD_ll, ONLY : FD_ll USE MODD_FM -TYPE(FD_ll), POINTER :: TPFD -TYPE(FMHEADER), INTENT(IN) :: TPFMH +TYPE(FD_ll), POINTER :: TPFD +TYPE(FMHEADER), INTENT(INOUT) :: TPFMH INTEGER :: ierr @@ -115,6 +116,28 @@ CALL MPI_BCAST(TPFMH%COMMENT,TPFMH%COMLEN,MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,I END SUBROUTINE BCAST_HEADER +SUBROUTINE IO_BCAST_FIELD_METADATA(TPFD,TPFIELD) +USE MODE_FD_ll, ONLY : FD_ll +TYPE(FD_ll), POINTER, INTENT(IN) :: TPFD +TYPE(TFIELDDATA), INTENT(INOUT) :: TPFIELD +! +INTEGER :: IERR +! +CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_BCAST_FIELD_METADATA','called for '//TRIM(TPFIELD%CMNHNAME)) +! +CALL MPI_BCAST(TPFIELD%CMNHNAME, LEN(TPFIELD%CMNHNAME), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CSTDNAME, LEN(TPFIELD%CSTDNAME), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CLONGNAME,LEN(TPFIELD%CLONGNAME),MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CUNITS, LEN(TPFIELD%CUNITS), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CDIR, LEN(TPFIELD%CDIR), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CLBTYPE, LEN(TPFIELD%CLBTYPE), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%CCOMMENT, LEN(TPFIELD%CCOMMENT), MPI_CHARACTER,TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%NGRID, 1, MPI_INTEGER, TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%NTYPE, 1, MPI_INTEGER, TPFD%OWNER-1,TPFD%COMM,IERR) +CALL MPI_BCAST(TPFIELD%NDIMS, 1, MPI_INTEGER, TPFD%OWNER-1,TPFD%COMM,IERR) +! +END SUBROUTINE IO_BCAST_FIELD_METADATA + SUBROUTINE FMREADX0_ll(HFILEM,HRECFM,HFIPRI,HDIR,PFIELD,KGRID,& KLENCH,HCOMMENT,KRESP) USE MODD_IO_ll, ONLY : ISP,GSMONOPROC @@ -1297,20 +1320,16 @@ END SUBROUTINE IO_READ_FIELD_BYNAME_N0 SUBROUTINE IO_READ_FIELD_BYFIELD_N0(TPFILE,TPFIELD,KFIELD,KRESP) ! USE MODD_IO_ll, ONLY : ISP,GSMONOPROC -USE MODD_FM USE MODE_FD_ll, ONLY : GETFD,FD_LL ! TYPE(TFILEDATA), INTENT(IN) :: TPFILE -TYPE(TFIELDDATA), INTENT(IN) :: TPFIELD +TYPE(TFIELDDATA), INTENT(INOUT) :: TPFIELD INTEGER, INTENT(INOUT) :: KFIELD ! array containing the data field INTEGER,OPTIONAL, INTENT(OUT) :: KRESP ! return-code ! INTEGER :: IERR TYPE(FD_ll), POINTER :: TZFD INTEGER :: IRESP -TYPE(FMHEADER) :: TZFMH -CHARACTER(LEN=:),ALLOCATABLE :: YMSG -CHARACTER(LEN=6) :: YRESP ! CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_FIELD_BYFIELD_N0',TRIM(TPFILE%CNAME)//': reading '//TRIM(TPFIELD%CMNHNAME)) ! @@ -1320,38 +1339,32 @@ TZFD=>GETFD(TRIM(ADJUSTL(TPFILE%CNAME))//'.lfi') IF (ASSOCIATED(TZFD)) THEN IF (GSMONOPROC) THEN ! sequential execution IF (ASSOCIATED(TZFD%CDF)) THEN - CALL IO_READ_FIELD_NC4(TPFILE,TPFIELD,KFIELD,TZFMH,IRESP) + CALL IO_READ_FIELD_NC4(TPFILE,TPFIELD,KFIELD,IRESP) ELSE - CALL FM_READ_ll(TZFD%FLU,TPFIELD%CMNHNAME,.FALSE.,1,KFIELD,TZFMH,IRESP) + CALL IO_READ_FIELD_LFI(TPFILE,TPFIELD,KFIELD,IRESP) END IF ELSE IF (ISP == TZFD%OWNER) THEN IF (ASSOCIATED(TZFD%CDF)) THEN - CALL IO_READ_FIELD_NC4(TPFILE,TPFIELD,KFIELD,TZFMH,IRESP) + CALL IO_READ_FIELD_NC4(TPFILE,TPFIELD,KFIELD,IRESP) ELSE - CALL FM_READ_ll(TZFD%FLU,TPFIELD%CMNHNAME,.FALSE.,1,KFIELD,TZFMH,IRESP) + CALL IO_READ_FIELD_LFI(TPFILE,TPFIELD,KFIELD,IRESP) END IF END IF ! CALL MPI_BCAST(IRESP,1,MPI_INTEGER,TZFD%OWNER-1,TZFD%COMM,IERR) ! - CALL BCAST_HEADER(TZFD,TZFMH) + !Broadcast header only if IRESP==-111 + !because metadata of field has been modified in IO_READ_FIELD_xxx + IF (IRESP==-111) CALL IO_BCAST_FIELD_METADATA(TZFD,TPFIELD) ! CALL MPI_BCAST(KFIELD,1,MPI_INTEGER,TZFD%OWNER-1,TZFD%COMM,IERR) END IF -! KGRID = TZFMH%GRID -! HCOMMENT = TZFMH%COMMENT(1:TZFMH%COMLEN) ELSE IRESP = -61 CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_FIELD_BYFIELD_N0','file '//TRIM(TPFILE%CNAME)//' not found') END IF ! -IF (IRESP.NE.0) THEN - WRITE(YRESP, '( I6 )') IRESP - YMSG = 'RESP='//YRESP//' when reading '//TRIM(TPFIELD%CMNHNAME)//' in '//TRIM(TPFILE%CNAME) - CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_FIELD_BYFIELD_N0',YMSG) -ENDIF -! IF (PRESENT(KRESP)) KRESP = IRESP ! END SUBROUTINE IO_READ_FIELD_BYFIELD_N0 diff --git a/src/LIB/SURCOUCHE/src/fmreadwrit.f90 b/src/LIB/SURCOUCHE/src/fmreadwrit.f90 index a235ff73d..7786a519a 100644 --- a/src/LIB/SURCOUCHE/src/fmreadwrit.f90 +++ b/src/LIB/SURCOUCHE/src/fmreadwrit.f90 @@ -300,7 +300,7 @@ PUBLIC IO_READ_FIELD_LFI,IO_WRITE_FIELD_LFI ! CONTAINS ! -SUBROUTINE IO_READ_FIELD_LFI_N0(TPFILE,TPFIELD,KFIELD,TPFMH,KRESP) +SUBROUTINE IO_READ_FIELD_LFI_N0(TPFILE,TPFIELD,KFIELD,KRESP) USE MODD_FM USE MODD_CONFZ, ONLY : NZ_VERB USE MODE_MSG @@ -309,11 +309,10 @@ IMPLICIT NONE ! !* 0.1 Declarations of arguments ! -TYPE(TFILEDATA), INTENT(IN) :: TPFILE -TYPE(TFIELDDATA),INTENT(IN) :: TPFIELD -INTEGER, INTENT(OUT) :: KFIELD ! array containing the data field -TYPE(FMHEADER), INTENT(OUT) :: TPFMH ! FM-File Header -INTEGER, INTENT(OUT) :: KRESP ! return-code if problems occured +TYPE(TFILEDATA), INTENT(IN) :: TPFILE +TYPE(TFIELDDATA),INTENT(INOUT) :: TPFIELD +INTEGER, INTENT(OUT) :: KFIELD ! array containing the data field +INTEGER, INTENT(OUT) :: KRESP ! return-code if problems occured ! !* 0.2 Declarations of local variables ! @@ -325,9 +324,9 @@ CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_FIELD_LFI_N0',TRIM(TPFILE%CNAME)//': re ! ILENG = 1 ! -CALL IO_READ_AND_CHECK_FIELD_LFI(TPFILE,TPFIELD,ILENG,IWORK,ITOTAL,TPFMH,IRESP) +CALL IO_READ_CHECK_FIELD_LFI(TPFILE,TPFIELD,ILENG,IWORK,ITOTAL,IRESP) ! -IF (IRESP==0) KFIELD = IWORK(TPFMH%COMLEN+3) +IF (IRESP==0) KFIELD = IWORK(IWORK(2)+3) ! KRESP=IRESP ! @@ -336,20 +335,23 @@ IF (ALLOCATED(IWORK)) DEALLOCATE(IWORK) END SUBROUTINE IO_READ_FIELD_LFI_N0 ! ! -SUBROUTINE IO_READ_AND_CHECK_FIELD_LFI(TPFILE,TPFIELD,KLENG,KWORK,KTOTAL,TPFMH,KRESP) +SUBROUTINE IO_READ_CHECK_FIELD_LFI(TPFILE,TPFIELD,KLENG,KWORK,KTOTAL,KRESP) ! TYPE(TFILEDATA), INTENT(IN) :: TPFILE -TYPE(TFIELDDATA), INTENT(IN) :: TPFIELD +TYPE(TFIELDDATA), INTENT(INOUT) :: TPFIELD INTEGER, INTENT(IN) :: KLENG INTEGER(KIND=8),DIMENSION(:),ALLOCATABLE,INTENT(OUT) :: KWORK INTEGER(KIND=LFI_INT), INTENT(OUT) :: KTOTAL -TYPE(FMHEADER), INTENT(OUT) :: TPFMH ! FM-File Header INTEGER(KIND=LFI_INT), INTENT(OUT) :: KRESP ! -INTEGER :: IROW,J -INTEGER,DIMENSION(JPXKRK) :: ICOMMENT -INTEGER(KIND=LFI_INT) :: INUMBR,IPOSEX -CHARACTER(LEN=12) :: YRECLENGTH_FILE, YRECLENGTH_MEM +INTEGER :: IROW,J +INTEGER,DIMENSION(JPXKRK) :: ICOMMENT +INTEGER(KIND=LFI_INT) :: ICOMLEN,INUMBR,IPOSEX +CHARACTER(LEN=:),ALLOCATABLE :: YMSG +CHARACTER(LEN=12) :: YRECLENGTH_FILE, YRECLENGTH_MEM +CHARACTER(LEN=12) :: YVAL_FILE, YVAL_MEM +CHARACTER(LEN=JPXKRK) :: YCOMMENT +CHARACTER(LEN=12) :: YRESP ! !* 2.a LET'S GET SOME INFORMATION ON THE DESIRED ARTICLE ! @@ -357,14 +359,17 @@ INUMBR = TPFILE%NLFIFLU CALL LFINFO(KRESP,INUMBR,TRIM(TPFIELD%CMNHNAME),KTOTAL,IPOSEX) ! IF (KRESP.NE.0) THEN + WRITE(YRESP, '( I12 )') KRESP + YMSG = 'RESP='//TRIM(ADJUSTL(YRESP))//' in call to LFINFO when reading '//TRIM(TPFIELD%CMNHNAME)//' in '//TRIM(TPFILE%CNAME) + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_LFI',YMSG) RETURN ELSEIF (KTOTAL.EQ.0) THEN - CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_AND_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': record length is zero for ' & + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': record length is zero for ' & //TRIM(TPFIELD%CMNHNAME)) KRESP=-47 RETURN ELSEIF (KTOTAL.GT.JPXFIE) THEN - CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_AND_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)// & + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)// & ': record length exceeds the maximum value in FM for '//TRIM(TPFIELD%CMNHNAME)) KRESP=-48 RETURN @@ -375,46 +380,72 @@ ENDIF ALLOCATE(KWORK(KTOTAL)) ! CALL LFILEC(KRESP,INUMBR,TRIM(TPFIELD%CMNHNAME),KWORK,KTOTAL) -IF (KRESP.NE.0) RETURN +IF (KRESP.NE.0) THEN + WRITE(YRESP, '( I12 )') KRESP + YMSG = 'RESP='//TRIM(ADJUSTL(YRESP))//' in call to LFILEC when reading '//TRIM(TPFIELD%CMNHNAME)//' in '//TRIM(TPFILE%CNAME) + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_LFI',YMSG) + RETURN +ENDIF ! !* 2.c THE GRID INDICATOR AND THE COMMENT STRING !* ARE SEPARATED FROM THE DATA ! -TPFMH%GRID = KWORK(1) -TPFMH%COMLEN = KWORK(2) -! -IROW=KLENG+TPFMH%COMLEN+2 +ICOMLEN = KWORK(2) +IROW=KLENG+ICOMLEN+2 IF (KTOTAL.NE.IROW) THEN - WRITE(YRECLENGTH_FILE,'(I12)') KTOTAL-2-TPFMH%COMLEN + WRITE(YRECLENGTH_FILE,'(I12)') KTOTAL-2-ICOMLEN WRITE(YRECLENGTH_MEM, '(I12)') KLENG - CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_AND_CHECK_FIELD_LFI','wrong field size for '//TRIM(TPFIELD%CMNHNAME) & + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_LFI','wrong field size for '//TRIM(TPFIELD%CMNHNAME) & //' (expected: '//TRIM(ADJUSTL(YRECLENGTH_MEM))// & ', in file: ' //TRIM(ADJUSTL(YRECLENGTH_FILE))//')') KRESP=-63 RETURN ENDIF ! -SELECT CASE (TPFMH%COMLEN) +IF (KWORK(1)/=TPFIELD%NGRID) THEN + WRITE(YVAL_FILE,'(I12)') KWORK(1) + WRITE(YVAL_MEM, '(I12)') TPFIELD%NGRID + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_LFI','expected GRID value ('//TRIM(ADJUSTL(YVAL_MEM))// & + ') is different than found in file ('//TRIM(ADJUSTL(YVAL_FILE))//') for variable '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%NGRID = KWORK(1) + KRESP = -111 !Used later to broadcast modified metadata +ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_LFI','expected GRID found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) +ENDIF +! +YCOMMENT='' +SELECT CASE (ICOMLEN) CASE(:-1) - CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_AND_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': comment length is negative for ' & + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': comment length is negative for ' & //TRIM(TPFIELD%CMNHNAME)) KRESP=-58 RETURN CASE(0) KRESP = 0 CASE(1:JPXKRK) - ICOMMENT(1:TPFMH%COMLEN)=KWORK(3:TPFMH%COMLEN+2) - DO J=1,TPFMH%COMLEN - TPFMH%COMMENT(J:J)=CHAR(ICOMMENT(J)) + ICOMMENT(1:ICOMLEN)=KWORK(3:ICOMLEN+2) + DO J=1,ICOMLEN + YCOMMENT(J:J)=CHAR(ICOMMENT(J)) ENDDO CASE(JPXKRK+1:) - CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_AND_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': comment is too long in file for ' & + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_LFI',TRIM(TPFILE%CNAME)//': comment is too long in file for ' & //TRIM(TPFIELD%CMNHNAME)) KRESP=-56 RETURN END SELECT ! -END SUBROUTINE IO_READ_AND_CHECK_FIELD_LFI +IF (TRIM(YCOMMENT)/=TRIM(TPFIELD%CCOMMENT)) THEN + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_LFI','expected COMMENT ('//TRIM(TPFIELD%CCOMMENT)// & + ') is different than found ('//TRIM(YCOMMENT)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%CCOMMENT=TRIM(YCOMMENT) + KRESP = -111 !Used later to broadcast modified metadata +ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_LFI','expected COMMENT found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) +END IF +! +END SUBROUTINE IO_READ_CHECK_FIELD_LFI ! ! SUBROUTINE IO_WRITE_FIELD_LFI_X0(TPFIELD,KFLU,PFIELD,KRESP) diff --git a/src/LIB/SURCOUCHE/src/mode_io.f90 b/src/LIB/SURCOUCHE/src/mode_io.f90 index 79ea2978f..f5b365a1e 100644 --- a/src/LIB/SURCOUCHE/src/mode_io.f90 +++ b/src/LIB/SURCOUCHE/src/mode_io.f90 @@ -983,7 +983,7 @@ CHARACTER(LEN=*),INTENT(IN) :: HMSG !Message ! INTEGER :: IERR, IMAXVERB,IABORTLEVEL CHARACTER(LEN=9) :: YPRE -CHARACTER(LEN=28) :: YSUBR +CHARACTER(LEN=30) :: YSUBR ! SELECT CASE(HDOMAIN) CASE('IO') @@ -1015,7 +1015,7 @@ SELECT CASE(KVERB) END SELECT ! YSUBR=TRIM(HSUBR)//':' -WRITE (*,"(A9,A28,A)") YPRE,YSUBR,HMSG +WRITE (*,"(A9,A30,A)") YPRE,YSUBR,HMSG ! IF (KVERB<=IABORTLEVEL) THEN PRINT *,'ABORT asked by application' diff --git a/src/LIB/SURCOUCHE/src/mode_netcdf.f90 b/src/LIB/SURCOUCHE/src/mode_netcdf.f90 index 802eea843..17f13db75 100644 --- a/src/LIB/SURCOUCHE/src/mode_netcdf.f90 +++ b/src/LIB/SURCOUCHE/src/mode_netcdf.f90 @@ -1727,7 +1727,7 @@ CALL PRINT_MSG(NVERB_DEBUG,'IO','NCWRITC0','writing '//TRIM(HVARNAME)) IRESP = 0 YSTR = HFIELD IF (LEN_TRIM(HFIELD) > LEN(YSTR)) THEN - PRINT *,'NCWRIT0 : ',TRIM(YVARNAME), ' string variable TRUNCATED.' + PRINT *,'NCWRITC0 : ',TRIM(YVARNAME), ' string variable TRUNCATED.' END IF ! Get the Netcdf file ID @@ -2067,6 +2067,177 @@ ELSE END IF END SUBROUTINE READATTR +SUBROUTINE IO_READ_CHECK_FIELD_ATTR_NC4(TPFIELD,KNCID,KVARID,KRESP,HCALENDAR) +! +TYPE(TFIELDDATA), INTENT(INOUT) :: TPFIELD +INTEGER(KIND=IDCDF_KIND), INTENT(IN) :: KNCID +INTEGER(KIND=IDCDF_KIND), INTENT(IN) :: KVARID +INTEGER, INTENT(OUT) :: KRESP ! return-code +CHARACTER(LEN=*),OPTIONAL,INTENT(IN) :: HCALENDAR +! +INTEGER :: ILEN +INTEGER :: IGRID +INTEGER(KIND=IDCDF_KIND) :: STATUS +CHARACTER(LEN=12) :: YVAL_FILE, YVAL_MEM +CHARACTER(LEN=:),ALLOCATABLE :: YVALUE +! +CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','called for field '//TRIM(TPFIELD%CMNHNAME)) +! +KRESP = 0 +! +! GRID +! +STATUS = NF90_GET_ATT(KNCID,KVARID,'GRID',IGRID) +IF (STATUS == NF90_NOERR) THEN + IF (IGRID/=TPFIELD%NGRID) THEN + WRITE(YVAL_FILE,'(I12)') IGRID + WRITE(YVAL_MEM, '(I12)') TPFIELD%NGRID + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected GRID value ('//TRIM(ADJUSTL(YVAL_MEM))// & + ') is different than found in file ('//TRIM(ADJUSTL(YVAL_FILE))//') for variable '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%NGRID = IGRID + KRESP = -111 !Used later to broadcast modified metadata + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected GRID found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ENDIF +ELSE !no GRID + IF (TPFIELD%NGRID==0 .OR. TPFIELD%NGRID==-1) THEN + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','no GRID (as expected) in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected GRID but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF +ENDIF +! +! COMMENT +! +STATUS = NF90_INQUIRE_ATTRIBUTE(KNCID, KVARID, 'COMMENT', LEN=ILEN) +IF (STATUS == NF90_NOERR) THEN + ALLOCATE(CHARACTER(LEN=ILEN) :: YVALUE) + STATUS = NF90_GET_ATT(KNCID, KVARID, 'COMMENT', YVALUE) + IF (TRIM(YVALUE)/=TRIM(TPFIELD%CCOMMENT)) THEN + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected COMMENT ('//TRIM(TPFIELD%CCOMMENT)// & + ') is different than found ('//TRIM(YVALUE)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%CCOMMENT=TRIM(YVALUE) + KRESP = -111 !Used later to broadcast modified metadata + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected COMMENT found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF + DEALLOCATE(YVALUE) +ELSE !no COMMENT + IF (LEN_TRIM(TPFIELD%CCOMMENT)==0) THEN + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','no COMMENT (as expected) in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected COMMENT but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF +END IF +! +! STDNAME +! +STATUS = NF90_INQUIRE_ATTRIBUTE(KNCID, KVARID, 'STDNAME', LEN=ILEN) +IF (STATUS == NF90_NOERR) THEN + ALLOCATE(CHARACTER(LEN=ILEN) :: YVALUE) + STATUS = NF90_GET_ATT(KNCID, KVARID, 'STDNAME', YVALUE) + IF (TRIM(YVALUE)/=TRIM(TPFIELD%CSTDNAME)) THEN + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected STDNAME ('//TRIM(TPFIELD%CSTDNAME)// & + ') is different than found ('//TRIM(YVALUE)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%CSTDNAME=TRIM(YVALUE) + KRESP = -111 !Used later to broadcast modified metadata + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected STDNAME found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF + DEALLOCATE(YVALUE) +ELSE !no STDNAME + IF (LEN_TRIM(TPFIELD%CSTDNAME)==0) THEN + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','no STDNAME (as expected) in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected STDNAME but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF +END IF +! +! LONGNAME +! +STATUS = NF90_INQUIRE_ATTRIBUTE(KNCID, KVARID, 'LONGNAME', LEN=ILEN) +IF (STATUS == NF90_NOERR) THEN + ALLOCATE(CHARACTER(LEN=ILEN) :: YVALUE) + STATUS = NF90_GET_ATT(KNCID, KVARID, 'LONGNAME', YVALUE) + IF (TRIM(YVALUE)/=TRIM(TPFIELD%CLONGNAME)) THEN + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected LONGNAME ('//TRIM(TPFIELD%CLONGNAME)// & + ') is different than found ('//TRIM(YVALUE)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%CLONGNAME=TRIM(YVALUE) + KRESP = -111 !Used later to broadcast modified metadata + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected LONGNAME found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF + DEALLOCATE(YVALUE) +ELSE !no LONGNAME + IF (LEN_TRIM(TPFIELD%CLONGNAME)==0) THEN + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','no LONGNAME (as expected) in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected LONGNAME but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF +END IF +! +! UNITS +! +STATUS = NF90_INQUIRE_ATTRIBUTE(KNCID, KVARID, 'UNITS', LEN=ILEN) +IF (STATUS == NF90_NOERR) THEN + ALLOCATE(CHARACTER(LEN=ILEN) :: YVALUE) + STATUS = NF90_GET_ATT(KNCID, KVARID, 'UNITS', YVALUE) + IF (TRIM(YVALUE)/=TRIM(TPFIELD%CUNITS)) THEN + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected UNITS ('//TRIM(TPFIELD%CUNITS)// & + ') is different than found ('//TRIM(YVALUE)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + TPFIELD%CUNITS=TRIM(YVALUE) + KRESP = -111 !Used later to broadcast modified metadata + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected UNITS found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF + DEALLOCATE(YVALUE) +ELSE !no UNITS + IF (LEN_TRIM(TPFIELD%CUNITS)==0) THEN + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','no UNITS (as expected) in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected UNITS but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF +END IF +! +! CALENDAR +! +IF(PRESENT(HCALENDAR)) THEN +STATUS = NF90_INQUIRE_ATTRIBUTE(KNCID, KVARID, 'CALENDAR', LEN=ILEN) +IF (STATUS == NF90_NOERR) THEN + ALLOCATE(CHARACTER(LEN=ILEN) :: YVALUE) + STATUS = NF90_GET_ATT(KNCID, KVARID, 'CALENDAR', YVALUE) + IF (TRIM(YVALUE)/=TRIM(HCALENDAR)) THEN + CALL PRINT_MSG(NVERB_WARNING,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected CALENDAR ('//TRIM(HCALENDAR)// & + ') is different than found ('//TRIM(YVALUE)//')in file for field '//TRIM(TPFIELD%CMNHNAME)) + ELSE + CALL PRINT_MSG(NVERB_DEBUG,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected CALENDAR found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) + END IF + DEALLOCATE(YVALUE) +ELSE !no CALENDAR + CALL PRINT_MSG(NVERB_INFO,'IO','IO_READ_CHECK_FIELD_ATTR_NC4','expected CALENDAR but not found in file for field ' & + //TRIM(TPFIELD%CMNHNAME)) +END IF +ENDIF +! +END SUBROUTINE IO_READ_CHECK_FIELD_ATTR_NC4 + + SUBROUTINE NCREADX0(KNCID, HVARNAME, PFIELD, TPFMH, KRESP) USE MODD_FM, ONLY : FMHEADER, JPXKRK INTEGER(KIND=IDCDF_KIND),INTENT(IN) :: KNCID @@ -2588,20 +2759,18 @@ KRESP = IRESP END SUBROUTINE NCREADN0 -SUBROUTINE IO_READ_FIELD_NC4_N0(TPFILE, TPFIELD, KFIELD, TPFMH, KRESP) +SUBROUTINE IO_READ_FIELD_NC4_N0(TPFILE, TPFIELD, KFIELD, KRESP) USE MODD_FM, ONLY : FMHEADER, JPXKRK -TYPE(TFILEDATA), INTENT(IN) :: TPFILE -TYPE(TFIELDDATA), INTENT(IN) :: TPFIELD -INTEGER, INTENT(OUT):: KFIELD -TYPE(FMHEADER), INTENT(OUT):: TPFMH -INTEGER, INTENT(OUT):: KRESP ! return-code +TYPE(TFILEDATA), INTENT(IN) :: TPFILE +TYPE(TFIELDDATA), INTENT(INOUT) :: TPFIELD +INTEGER, INTENT(OUT) :: KFIELD +INTEGER, INTENT(OUT) :: KRESP ! return-code INTEGER(KIND=IDCDF_KIND) :: STATUS INTEGER(KIND=IDCDF_KIND) :: INCID INTEGER(KIND=IDCDF_KIND) :: IVARID INTEGER(KIND=IDCDF_KIND) :: ITYPE ! variable type INTEGER(KIND=IDCDF_KIND) :: IDIMS ! number of dimensions -INTEGER(KIND=IDCDF_KIND) :: ICOMLEN ! comment length CHARACTER(LEN=30) :: YVARNAME INTEGER :: IRESP @@ -2634,10 +2803,11 @@ IF (IDIMS == 0 .AND. (ITYPE == NF90_INT64 .OR. ITYPE == NF90_INT1) ) THEN CALL HANDLE_ERR(status,__LINE__,'IO_READ_FIELD_NC4_N0[NF90_GET_VAR] '//TRIM(YVARNAME),IRESP) GOTO 1000 END IF - ! Read variables attributes (GRID and COMMENT) - CALL READATTR(INCID, IVARID, YVARNAME, TPFMH) + ! Read and check attributes of variable + CALL IO_READ_CHECK_FIELD_ATTR_NC4(TPFIELD,INCID,IVARID,IRESP) ELSE - PRINT *, 'IO_READ_FIELD_NC4_N0: '//TRIM(YVARNAME)//' not READ (wrong size or type).' + CALL PRINT_MSG(NVERB_ERROR,'IO','IO_READ_FIELD_NC4_N0',TRIM(TPFILE%CNAME)//': '//TRIM(YVARNAME)// & + ' not read (wrong size or type)') IRESP = -3 END IF -- GitLab