1 subroutine addgrid
(cgrib
,lcgrib
,igds
,igdstmpl
,igdstmplen
,
2 & ideflist
,idefnum
,ierr
)
3 !$$$ SUBPROGRAM DOCUMENTATION BLOCK
6 ! PRGMMR
: Gilbert ORG
: W
/NP11
DATE: 2000-05-01
8 ! ABSTRACT
: This
subroutine packs up a Grid Definition Section
(Section
3)
9 ! and adds it
to a GRIB2 message
.
10 ! This routine is used with routines
"gribcreate", "addlocal", "addfield",
11 ! and
"gribend" to create a complete GRIB2 message
. Subroutine
12 ! gribcreate must be called first
to initialize a new GRIB2 message
.
14 ! PROGRAM HISTORY LOG
:
17 ! USAGE
: CALL addgrid
(cgrib
,lcgrib
,igds
,igdstmpl
,igdstmplen
,
18 ! ideflist
,idefnum
,ierr
)
19 ! INPUT ARGUMENT LIST
:
20 ! cgrib
- Character array
to contain the GRIB2 message
21 ! lcgrib
- Maximum length
(bytes
) of array cgrib
.
22 ! igds
- Contains information needed
for GRIB Grid Definition Section
3.
23 ! Must be dimensioned
>= 5.
24 ! igds
(1)=Source of grid definition
(see Code Table
3.0)
25 ! igds
(2)=Number of grid points in the defined grid
.
26 ! igds
(3)=Number of octets needed
for each
27 ! additional grid points definition
.
28 ! Used
to define number of
29 ! points in each row
( or column
) for
31 ! = 0, if using regular grid
.
32 ! igds
(4)=Interpretation of list
for optional points
33 ! definition
. (Code Table
3.11)
34 ! igds
(5)=Grid Definition Template Number
(Code Table
3.1)
35 ! igdstmpl
- Contains the data values
for the specified Grid Definition
36 ! Template
( NN
=igds
(5) ). Each element of this
integer
37 ! array contains an entry
(in the order specified
) of Grid
38 ! Defintion Template
3.NN
39 ! igdstmplen
- Max
dimension of igdstmpl
()
40 ! ideflist
- (Used
if igds
(3) .ne
. 0) This array contains the
41 ! number of grid points contained in each row
( or column
)
42 ! idefnum
- (Used
if igds
(3) .ne
. 0) The number of entries
43 ! in array ideflist
. i
.e
. number of rows
( or columns
)
44 ! for which optional grid points are defined
.
46 ! OUTPUT ARGUMENT LIST
:
47 ! cgrib
- Character array
to contain the GRIB2 message
48 ! ierr
- Error
return code
.
50 ! 1 = GRIB message was not initialized
. Need
to call
51 ! routine gribcreate first
.
52 ! 2 = GRIB message already complete
. Cannot add new section
.
53 ! 3 = Sum of Section byte counts doesn
't add to total byte count.
54 ! 4 = Previous Section was not 1, 2 or 7.
55 ! 5 = Could not find requested Grid Definition Template.
57 ! REMARKS: Note that the Local Use Section ( Section 2 ) can only follow
58 ! Section 1 or Section 7 in a GRIB2 message.
61 ! LANGUAGE: Fortran 90
68 character(len=1),intent(inout) :: cgrib(lcgrib)
69 integer,intent(in) :: igds(*),igdstmpl(*),ideflist(idefnum)
70 integer,intent(in) :: lcgrib,idefnum,igdstmplen
71 integer,intent(out) :: ierr
73 character(len=4),parameter :: grib='GRIB
',c7777='7777'
74 character(len=4):: ctemp
75 integer:: mapgrid(igdstmplen)
76 integer,parameter :: one=1,three=3
77 integer lensec3,iofst,ibeg,lencurr,len,mapgridlen
82 ! Check to see if beginning of GRIB message exists
84 ctemp=cgrib(1)//cgrib(2)//cgrib(3)//cgrib(4)
85 if ( ctemp.ne.grib ) then
86 print *,'addgrid
: GRIB not found in given message
.'
87 print *,'addgrid
: Call to routine gribcreate required
',
88 & ' to initialize GRIB messge
.'
93 ! Get current length of GRIB message
95 call gbyte(cgrib,lencurr,96,32)
97 ! Check to see if GRIB message is already complete
99 ctemp=cgrib(lencurr-3)//cgrib(lencurr-2)//cgrib(lencurr-1)
101 if ( ctemp.eq.c7777 ) then
102 print *,'addgrid
: GRIB message already complete
. Cannot
',
103 & ' add new section
.'
108 ! Loop through all current sections of the GRIB message to
109 ! find the last section number.
111 len=16 ! length of Section 0
113 ! Get section number and length of next section
115 call gbyte(cgrib,ilen,iofst,32)
117 call gbyte(cgrib,isecnum,iofst,8)
119 ! Exit loop if last section reached
120 if ( len.eq.lencurr ) exit
121 ! If byte count for each section doesn't match current
122 ! total length
, then there is a problem
.
123 if ( len
.gt
.lencurr
) then
124 print
*,'addgrid: Section byte counts don''t add to total.'
125 print
*,'addgrid: Sum of section byte counts = ',len
126 print
*,'addgrid: Total byte count in Section 0 = ',lencurr
132 ! Section
3 can only be added after sections
1, 2 and
7.
134 if ( (isecnum
.ne
.1) .and
. (isecnum
.ne
.2) .and
.
135 & (isecnum
.ne
.7) ) then
136 print
*,'addgrid: Section 3 can only be added after Section',
138 print
*,'addgrid: Section ',isecnum
,' was the last found in',
139 & ' given GRIB message.'
144 ! Add Section
3 - Grid Definition Section
146 ibeg
=lencurr*8
! Calculate offset
for beginning of section
3
147 iofst
=ibeg
+32 ! leave space
for length of section
148 call sbyte
(cgrib
,three
,iofst
,8) ! Store section number
( 3 )
150 call sbyte
(cgrib
,igds
(1),iofst
,8) ! Store source of Grid def
.
152 call sbyte
(cgrib
,igds
(2),iofst
,32) ! Store number of data pts
.
154 call sbyte
(cgrib
,igds
(3),iofst
,8) ! Store number of extra octets
.
156 call sbyte
(cgrib
,igds
(4),iofst
,8) ! Store interp
. of extra octets
.
158 ! if Octet
6 is not equal
to zero
, Grid Definition Template may
160 if ( igds
(1).eq
.0 ) then
161 call sbyte
(cgrib
,igds
(5),iofst
,16) ! Store Grid Def Template num
.
163 call sbyte
(cgrib
,65535,iofst
,16) ! Store missing value as Grid Def Template num
.
167 ! Get Grid Definition Template
169 if (igds
(1).eq
.0) then
170 call getgridtemplate
(igds
(5),mapgridlen
,mapgrid
,needext
,
177 ! Extend the Grid Definition Template
, if necessary
.
178 ! The number of values in a specific template may vary
179 ! depending on data specified in the
"static" part of the
183 call extgridtemplate
(igds
(5),igdstmpl
,mapgridlen
,mapgrid
)
189 ! Pack up each input value in array igdstmpl into the
190 ! the appropriate number of octets
, which are specified in
191 ! corresponding entries in array mapgrid
.
194 nbits
=iabs
(mapgrid
(i
))*8
195 if ( (mapgrid
(i
).ge
.0).or
.(igdstmpl
(i
).ge
.0) ) then
196 call sbyte
(cgrib
,igdstmpl
(i
),iofst
,nbits
)
198 call sbyte
(cgrib
,one
,iofst
,1)
199 call sbyte
(cgrib
,iabs
(igdstmpl
(i
)),iofst
+1,nbits
-1)
205 ! Insert optional list of numbers defining number of points
206 ! in each row or column
. This is used
for non regular
209 if ( igds
(3).ne
.0 ) then
211 call sbytes
(cgrib
,ideflist
,iofst
,nbits
,0,idefnum
)
212 iofst
=iofst
+(nbits*idefnum
)
215 ! Calculate length of section
3 and store it in octets
218 lensec3
=(iofst
-ibeg
)/8
219 call sbyte
(cgrib
,lensec3
,ibeg
,32)
222 ! Update current byte total of message in Section
0
224 call sbyte
(cgrib
,lencurr
+lensec3
,96,32)