SUBROUTINE CX_DCOD ( lutblb, lutbld, mxndesc, mxrpt, mxrptsz, + mxdatv, lenmsg, crexmsg, ctbla, ctblds, + ndesc, datadesc, nmrpts, nmdesc, expdesc, + lenrpts, rawrpt, nmdatval, dataval, + iret ) C************************************************************************ C* CX_DCOD * C* * C* This program decodes a CREX message and places the information * C* extracted from the message into selected arrays for the user. The * C* user passes to the program the unit numbers for CREX Tables B and D, * C* the maximum number of descriptors expected in Section 1 of the * C* message, the maximum number of data values expected in a report * C* (subset), and the maximum number of reports expected in the message. * C* This allows for realistic sizing of the arrays in the program. * C* * C* CX_DCOD ( LUTBLB, LUTBLD, MXNDESC, MXRPT, MXRPTSZ, MXDATV, LENMSG, * C* CREXMSG, CTBLA, CTBLDS, NDESC, DATADESC, NMRPTS, EXPDESC, * C* LENRPTS, RAWRPT, NMDATVAL, DATAVAL, IRET ) * C* * C* INPUT PARAMETERS: * C* LUTBLB INTEGER CREX Table B logical unit number* C* LUTBLD INTEGER CREX Table D logical unit number* C* MXNDESC INTEGER Maximum number of descriptors * C* expected in Section 1 of message* C* MXRPT INTEGER Maximum number of reports * C* expected in message * C* MXRPTSZ INTEGER Maximum report size expected * C* MXDATV REAL Maximum number of data values * C* expected * C* LENMSG INTEGER CREX message length * C* CREXMSG CHAR* CREX message * C* * C* Output parameters: * C* CTBLA CHAR* 3-digit CREX table A reference * C* CTBLDS CHAR* CREX table descriptor * C* NDESC INTEGER Number of data descriptors in * C* Section 1 of CREX message * C* DATADESC (MXNDESC) * C* CHAR* List of descriptors in Sec 1 * C* * C* NMRPTS INTEGER Number of reports in CREX msg * C* * C* NMDESC INTEGER Number of descriptors in expdesc* C* * C* EXPDESC (MXDATV) * C* CHAR* List of the expanded Section 1 * C* descriptors. The expansion * C* consists of replacing the * C* sequence and non-delayed * C* replication descriptors with the* C* list they correspond to. The * C* final list will be close to a * C* one-to-one correspondence with * C* the data values in Section 2. * C* LENRPTS (NMRPTS) * C* INTEGER Array to store the length of * C* each report * C* RAWRPT (MXRPT, MXRPTSZ) * C* CHAR* Array to hold subsets in message* C* * C* NMDATVAL INTEGER Number of data values in * C* Section 2 of CREX message * C* * C* DATAVAL (MXRPT,MXDATV) * C* REAL Array to hold the Section 2 * C* decoded data values * C* * C* IRET INTEGER Return code * C* 0 = Normal return * C* 1 = Problems * C* * C** * C* Log: * C* R. Hollern/NCEP 8/03 * C************************************************************************ INCLUDE 'GEMPRM.PRM' INCLUDE 'BRIDGE.PRM' INCLUDE 'cxcmn.cmn' C* REAL*8 dataval ( mxrpt, mxdatv ), rtemp C* CHARACTER datadesc ( mxndesc )*6 C* INTEGER lcxrpt, lenmsg, chkdge INTEGER lenrpts ( mxrpt ) C* CHARACTER*(*) crexmsg C* CHARACTER rawrpt ( mxrpt, mxrptsz )*8 CHARACTER expdesc ( mxdatv )*6 CHARACTER sortdesc ( mxdatv )*6 CHARACTER ctemp*8, misng*8 C* CHARACTER ctbla*4, ctblds*7 C* CHARACTER cxrpt*( DCMXBF ) C* LOGICAL first / .true. / LOGICAL more, good, ibufr, last C* EQUIVALENCE ( ctemp, rtemp ) C* DATA misng / '////////' / C* SAVE first C----------------------------------------------------------------------- iret = 0 nmrpts = 0 jst = 0 C IF ( first ) THEN C first = .false. C C* Read the CREX Sequence Table D. C CALL CX_TBLD ( lutbld, ierr ) C IF ( ierr .ne. 0 ) THEN C C* Fatal error. C iret = 1 RETURN END IF C C* Read the CREX Sequence Table B. C CALL CX_TBLB ( lutblb, ierr ) C IF ( ierr .ne. 0 ) THEN C C* Fatal error. C iret = 1 RETURN END IF C END IF C C* Initialize decoded data values array to all missing. C ctemp = misng C DO i = 1,mxrpt DO j = 1,mxdatv dataval ( i, j ) = rtemp END DO END DO C C* Verify that Section 0 - Indicator Section and C* Section 4 - End Section are part of the message. C* Check if message contatins Section 3 - the Optional Section. C CALL CX_SECS ( lenmsg, crexmsg, jpos, iret ) C IF ( iret .eq. 1 ) RETURN C C* Decode Section 0, 1, and 4 of CREX message. C CALL CX_DCD1 ( lenmsg, crexmsg, mxndesc, jpos, ctbla, + ctblds, ndesc, datadesc, nmdesc, mxdatv, + expdesc, nsdcr, sortdesc, chkdge, iret ) C IF ( iret .eq. 1 ) THEN C C* Message rejected. C RETURN END IF C C* Loop through reports. C more = .true. C DO WHILE ( more ) good = .true. C C* Get next report from bulletin. C CALL CX_GRPT ( lenmsg, crexmsg, mxrpt, mxrptsz, jpos, + lcxrpt, cxrpt, nmrpts, lenrpts, rawrpt, + iret ) C IF ( iret .eq. 1 ) THEN C C* Report not formatted correctly. C RETURN ELSE IF ( iret .eq. 2 ) THEN C C* This is the last report in message. C more = .false. ELSE IF ( iret .eq. 3 ) THEN C C* No more reports in bulletin. C RETURN END IF C IF ( good ) THEN C C* Decode Section 2. C CALL CX_GETV( cxrpt, nsdcr, sortdesc, mxdatv, mxrpt, + nmrpts, nmdesc, expdesc, chkdge, + nmdatval, dataval, iret ) C IF ( iret .eq. 1 ) RETURN C END IF C END DO C C* Don't count the "ENDDSC" as one of the descriptors in C* datadesc and expdesc. C ndesc = ndesc - 1 nmdesc = nmdesc - 1 C* RETURN END