NCEPLIBS-bufr 11.7.1
cktaba.f
Go to the documentation of this file.
1C> @file
2C> @author WOOLLEN @date 2000-09-19
3
4C> THIS SUBROUTINE PARSES THE TABLE A MNEMONIC AND THE DATE
5C> OUT OF SECTION 1 OF A BUFR MESSAGE PREVIOUSLY READ FROM UNIT LUNIT
6C> USING BUFR ARCHIVE LIBRARY SUBROUTINE READMG OR EQUIVALENT (AND NOW
7C> STORED IN THE INTERNAL MESSAGE BUFFER, ARRAY MBAY IN MODULE
8C> BITBUF). THE TABLE A MNEMONIC IS ASSOCIATED WITH THE BUFR
9C> MESSAGE TYPE/SUBTYPE IN SECTION 1. IT ALSO FILLS IN THE MESSAGE
10C> CONTROL WORD PARTITION ARRAYS IN MODULE MSGCWD.
11C>
12C> PROGRAM HISTORY LOG:
13C> 2000-09-19 J. WOOLLEN -- ORIGINAL AUTHOR - CONSOLIDATED MESSAGE
14C> DECODING LOGIC THAT HAD BEEN REPLICATED IN
15C> READMG, READFT, READERME, RDMEMM AND READIBM
16C> (CKTABA IS NOW CALLED BY THESE CODES);
17C> LOGIC ENHANCED HERE TO ALLOW COMPRESSED AND
18C> STANDARD BUFR MESSAGES TO BE READ
19C> 2003-11-04 S. BENDER -- ADDED REMARKS/BUFRLIB ROUTINE
20C> INTERDEPENDENCIES
21C> 2003-11-04 D. KEYSER -- MODIFIED TO NOT ABORT WHEN THE SECTION 1
22C> MESSAGE SUBTYPE DOES NOT AGREE WITH THE
23C> SECTION 1 MESSAGE SUBTYPE IN THE DICTIONARY
24C> IF THE MESSAGE TYPE MNEMONIC IS NOT OF THE
25C> FORM "NCtttsss", WHERE ttt IS THE BUFR TYPE
26C> AND sss IS THE BUFR SUBTYPE (E.G., IN
27C> "PREPBUFR" FILES); MODIFIED DATE
28C> CALCULATIONS TO NO LONGER USE FLOATING
29C> POINT ARITHMETIC SINCE THIS CAN LEAD TO
30C> ROUND OFF ERROR AND AN IMPROPER RESULTING
31C> DATE ON SOME MACHINES (E.G., NCEP IBM
32C> FROST/SNOW), INCREASES PORTABILITY;
33C> UNIFIED/PORTABLE FOR WRF; ADDED
34C> DOCUMENTATION (INCLUDING HISTORY); OUTPUTS
35C> MORE COMPLETE DIAGNOSTIC INFO WHEN ROUTINE
36C> TERMINATES ABNORMALLY OR UNUSUAL THINGS
37C> HAPPEN; SUBSET DEFINED AS " " IF
38C> IRET RETURNED AS 11 (BEFORE WAS UNDEFINED)
39C> 2004-08-09 J. ATOR -- MAXIMUM MESSAGE LENGTH INCREASED FROM
40C> 20,000 TO 50,000 BYTES
41C> 2005-11-29 J. ATOR -- USE IUPBS01, IGETDATE AND GETLENS
42C> 2006-04-14 J. ATOR -- ALLOW "FRtttsss" AND "FNtttsss" AS POSSIBLE
43C> TABLE A MNEMONICS, WHERE ttt IS THE BUFR
44C> TYPE AND sss IS THE BUFR SUBTYPE
45C> 2009-03-23 J. ATOR -- ADD LOGIC TO ALLOW SECTION 3 DECODING;
46C> USE IUPBS3 AND ERRWRT
47C> 2014-12-10 J. ATOR -- USE MODULES INSTEAD OF COMMON BLOCKS
48C>
49C> USAGE: CALL CKTABA (LUN, SUBSET, JDATE, IRET)
50C> INPUT ARGUMENT LIST:
51C> LUN - INTEGER: I/O STREAM INDEX INTO INTERNAL MEMORY ARRAYS
52C>
53C> OUTPUT ARGUMENT LIST:
54C> SUBSET - CHARACTER*8: TABLE A MNEMONIC FOR TYPE OF BUFR MESSAGE
55C> BEING CHECKED:
56C> " " = IRET equal to 11 (see IRET below)
57C> and not using Section 3 decoding
58C> JDATE - INTEGER: DATE-TIME STORED WITHIN SECTION 1 OF BUFR
59C> MESSAGE BEING CHECKED, IN FORMAT OF EITHER YYMMDDHH OR
60C> YYYYMMDDHH, DEPENDING ON DATELEN() VALUE
61C> IRET - INTEGER: RETURN CODE:
62C> 0 = normal return
63C> -1 = unrecognized Table A (message type) value
64C> 11 = this is a BUFR table (dictionary) message
65C>
66C> REMARKS:
67C> THIS ROUTINE CALLS: BORT DIGIT ERRWRT GETLENS
68C> I4DY IGETDATE IUPB IUPBS01
69C> IUPBS3 NEMTBAX NUMTAB OPENBT
70C> RDUSDX
71C> THIS ROUTINE IS CALLED BY: RDMEMM READERME READMG
72C> Normally not called by any application
73C> programs.
74C>
75 SUBROUTINE cktaba(LUN,SUBSET,JDATE,IRET)
76
77 USE moda_msgcwd
78 USE moda_sc3bfr
79 USE moda_unptyp
80 USE moda_bitbuf
81
82 COMMON /padesc/ ibct,ipd1,ipd2,ipd3,ipd4
83 COMMON /quiet / iprt
84
85 CHARACTER*128 BORT_STR,ERRSTR
86 CHARACTER*8 SUBSET
87 CHARACTER*2 CPFX(3)
88 CHARACTER*1 TAB
89 LOGICAL TRYBT, DIGIT
90
91 DATA cpfx / 'NC', 'FR', 'FN' /
92 DATA ncpfx / 3 /
93
94C-----------------------------------------------------------------------
95C-----------------------------------------------------------------------
96
97 iret = 0
98
99 trybt = .true.
100
101 jdate = igetdate(mbay(1,lun),iyr,imo,idy,ihr)
102
103c .... Message type
104 mtyp = iupbs01(mbay(1,lun),'MTYP')
105c .... Message subtype
106 msbt = iupbs01(mbay(1,lun),'MSBT')
107
108 IF(mtyp.EQ.11) THEN
109c .... This is a BUFR table (dictionary) message.
110 iret = 11
111c .... There's no need to proceed any further unless Section 3 is being
112c .... used for decoding.
113 IF(isc3(lun).EQ.0) THEN
114 subset = " "
115 GOTO 100
116 ENDIF
117 ENDIF
118
119C PARSE SECTION 3
120C ---------------
121
122 CALL getlens(mbay(1,lun),3,len0,len1,len2,len3,l4,l5)
123
124 iad3 = len0+len1+len2
125
126c .... First descriptor (integer)
127 ksub = iupb(mbay(1,lun),iad3+8 ,16)
128c .... Second descriptor (integer)
129 isub = iupb(mbay(1,lun),iad3+10,16)
130
131C LOCATE SECTION 4
132C ----------------
133
134 iad4 = iad3+len3
135
136C NOW, TRY TO GET "SUBSET" (MNEMONIC ASSOCIATED WITH TABLE A) FROM MSG
137C --------------------------------------------------------------------
138
139C FIRST CHECK WHETHER SECTION 3 IS BEING USED FOR DECODING
140C --------------------------------------------------------
141
142 IF(isc3(lun).NE.0) THEN
143 subset = tamnem(lun)
144c .... is SUBSET from Table A?
145 CALL nemtbax(lun,subset,mty1,msb1,inod)
146 IF(inod.GT.0) THEN
147c .... yes it is
148 mbyt(lun) = 8*(iad4+4)
149 msgunp(lun) = 1
150 GOTO 10
151 ENDIF
152 ENDIF
153
154C IF ISUB FROM SECTION 3 DEFINES TABLE A THEN MSGUNP=0
155C ----------------------------------------------------
156
157c .... get SUBSET from ISUB
1585 CALL numtab(lun,isub,subset,tab,itab)
159c .... is SUBSET from Table A?
160 CALL nemtbax(lun,subset,mty1,msb1,inod)
161 IF(inod.GT.0) THEN
162c .... yes it is
163 mbyt(lun) = (iad4+4)
164 msgunp(lun) = 0
165 GOTO 10
166 ENDIF
167
168C IF KSUB FROM SECTION 3 DEFINES TABLE A THEN MSGUNP=1 (standard)
169C ---------------------------------------------------------------
170
171c .... get SUBSET from KSUB
172 CALL numtab(lun,ksub,subset,tab,itab)
173c .... is SUBSET from Table A?
174 CALL nemtbax(lun,subset,mty1,msb1,inod)
175 IF(inod.GT.0) THEN
176c .... yes it is
177 mbyt(lun) = 8*(iad4+4)
178 msgunp(lun) = 1
179 GOTO 10
180 ENDIF
181
182C OKAY, STILL NO "SUBSET", LETS MAKE IT "NCtttsss" (where ttt=MTYP
183C and sss=MSBT) AND SEE IF IT DEFINES TABLE A. IF NOT, THEN ALSO
184C TRY "FRtttsss" AND "FNtttsss".
185C ----------------------------------------------------------------
186
187 ii=1
188 DO WHILE(ii.LE.ncpfx)
189 WRITE(subset,'(A2,2I3.3)') cpfx(ii),mtyp,msbt
190c .... is SUBSET from Table A?
191 CALL nemtbax(lun,subset,mty1,msb1,inod)
192 IF(inod.GT.0) THEN
193c .... yes it is
194 IF(ksub.EQ.ibct) THEN
195 mbyt(lun) = (iad4+4)
196 msgunp(lun) = 0
197 ELSE
198 mbyt(lun) = 8*(iad4+4)
199 msgunp(lun) = 1
200 ENDIF
201 GOTO 10
202 ENDIF
203 ii=ii+1
204 ENDDO
205
206C NOW WE HAVE A GENERATED "SUBSET", BUT IT STILL DOES NOT DEFINE
207C TABLE A - MAKE ONE LAST DESPERATE ATTEMPT - SEE IF AN EXTERNAL
208C USER-SUPPLIED BUFR DICTIONARY TABLE IN CHARACTER FORMAT IS DEFINED
209C IN OPENBT (ONLY POSSIBLE IF APPLICATION PROGRAM HAS AN IN-LINE
210C OPENBT OVERRIDING THE ONE IN THE BUFR ARCHIVE LIBRARY)
211C ------------------------------------------------------------------
212
213 IF(trybt) THEN
214 trybt = .false.
215 IF(iprt.GE.1) THEN
216 CALL errwrt('++++++++++++++BUFR ARCHIVE LIBRARY+++++++++++++++++')
217 errstr = 'BUFRLIB: CKTABA - LAST RESORT, CHECK FOR EXTERNAL'//
218 . ' BUFR TABLE VIA CALL TO IN-LINE OPENBT'
219 CALL errwrt(errstr)
220 CALL errwrt('++++++++++++++BUFR ARCHIVE LIBRARY+++++++++++++++++')
221 CALL errwrt(' ')
222 ENDIF
223 CALL openbt(lundx,mtyp)
224 IF(lundx.GT.0) THEN
225c .... Good news, there is a unit (LUNDX) connected to a table file,
226c .... so store the table internally
227 CALL rdusdx(lundx,lun)
228 GOTO 5
229 ENDIF
230 ENDIF
231
232C IF ALL ATTEMPTS TO DEFINE TABLE A FAIL SKIP GIVE UP
233C ---------------------------------------------------
234
235 IF(iprt.GE.0) THEN
236 CALL errwrt('+++++++++++++++++++++WARNING+++++++++++++++++++++++')
237 errstr = 'BUFRLIB: CKTABA - UNRECOGNIZED TABLE A MESSAGE TYPE ('//
238 . subset // ') - RETURN WITH IRET = -1'
239 CALL errwrt(errstr)
240 CALL errwrt('+++++++++++++++++++++WARNING+++++++++++++++++++++++')
241 CALL errwrt(' ')
242 ENDIF
243 iret = -1
244 GOTO 100
245
246C CHECK THE VALIDITY OF THE MTYP/MSBT AND FOR COMPRESSION (MSGUNP=2)
247C ------------------------------------------------------------------
248
24910 IF(isc3(lun).EQ.0) THEN
250 IF(mtyp.NE.mty1) GOTO 900
251 IF(msbt.NE.msb1.AND.digit(subset(3:8))) GOTO 901
252 ENDIF
253 IF(iupbs3(mbay(1,lun),'ICMP').GT.0) msgunp(lun) = 2
254
255C SET THE OTHER REQUIRED PARAMETERS IN MESSAGE CONTROL WORD PARTITION
256C -------------------------------------------------------------------
257
258c .... Date for this message
259 idate(lun) = i4dy(jdate)
260c .... Positional index of Table A mnem.
261 inode(lun) = inod
262c .... Number of subsets in this message
263 msub(lun) = iupbs3(mbay(1,lun),'NSUB')
264c .... Number of subsets read so far from this message
265 nsub(lun) = 0
266
267 IF(iret.NE.11) THEN
268c .... Number of non-dictionary messages read so far from this file
269 nmsg(lun) = nmsg(lun)+1
270 ENDIF
271
272C EXITS
273C -----
274
275100 RETURN
276900 WRITE(bort_str,'("BUFRLIB: CKTABA - MESSAGE TYPE MISMATCH '//
277 . '(SUBSET=",A8,", MTYP=",I3,", MTY1=",I3)') subset,mtyp,mty1
278 CALL bort(bort_str)
279901 WRITE(bort_str,'("BUFRLIB: CKTABA - MESSAGE SUBTYPE MISMATCH '//
280 . '(SUBSET=",A8,", MSBT=",I3,", MSB1=",I3)') subset,msbt,msb1
281 CALL bort(bort_str)
282 END
subroutine bort(STR)
This subroutine calls subroutine errwrt() to log an error message, then calls subroutine bort_exit() ...
Definition: bort.f:23
subroutine cktaba(LUN, SUBSET, JDATE, IRET)
THIS SUBROUTINE PARSES THE TABLE A MNEMONIC AND THE DATE OUT OF SECTION 1 OF A BUFR MESSAGE PREVIOUSL...
Definition: cktaba.f:76
subroutine errwrt(STR)
This subroutine allows the user to specify a custom location for the logging of error and diagnostic ...
Definition: errwrt.f:42
subroutine getlens(MBAY, LL, LEN0, LEN1, LEN2, LEN3, LEN4, LEN5)
This subroutine reads the lengths of all of the individual sections of a given BUFR message,...
Definition: getlens.f:40
function i4dy(IDATE)
This function converts a date-time with a 2-digit year (YYMMDDHH) to a date-time with a 4-digit year ...
Definition: i4dy.f:32
function igetdate(MBAY, IYR, IMO, IDY, IHR)
This function returns the date-time from within Section 1 of a BUFR message.
Definition: igetdate.f:35
function iupb(MBAY, NBYT, NBIT)
THIS FUNCTION UNPACKS AND RETURNS A BINARY INTEGER WORD CONTAINED WITHIN NBIT BITS OF A BUFR MESSAGE ...
Definition: iupb.f:37
function iupbs01(MBAY, S01MNEM)
This function returns a specified value from within Section 0 or Section 1 of a BUFR message.
Definition: iupbs01.f:74
function iupbs3(MBAY, S3MNEM)
This function returns a specified value from within Section 3 of a BUFR message.
Definition: iupbs3.f:35
This module contains array and variable declarations used to store BUFR messages internally for multi...
Definition: moda_bitbuf.F:10
integer, dimension(:), allocatable mbyt
Length (in bytes) of current BUFR message for each internal I/O stream.
Definition: moda_bitbuf.F:25
integer, dimension(:,:), allocatable mbay
Current BUFR message for each internal I/O stream.
Definition: moda_bitbuf.F:26
subroutine nemtbax(LUN, NEMO, MTYP, MSBT, INOD)
This subroutine searches for a descriptor within Table A of the internal DX BUFR tables.
Definition: nemtbax.f:34
subroutine numtab(LUN, IDN, NEMO, TAB, IRET)
This subroutine returns information about a descriptor from the internal DX BUFR tables,...
Definition: numtab.f:59
subroutine openbt(LUNDX, MTYP)
This subroutine is called as a last resort from within subroutine cktaba(), in the event the latter s...
Definition: openbt.f:42
subroutine rdusdx(LUNDX, LUN)
THIS SUBROUTINE READS AND PARSES A FILE CONTAINING A USER- SUPPLIED BUFR DICTIONARY TABLE IN CHARACTE...
Definition: rdusdx.f:65