Coverage Report

Created: 2026-02-14 09:00

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/gdal/frmts/grib/degrib/g2clib/gridtemplates.c
Line
Count
Source
1
#include <stdlib.h>
2
#include "grib2.h"
3
#include "gridtemplates.h"
4
5
/* GDAL: in original g2clib, this is in gridtemplates.h */
6
static const struct gridtemplate templatesgrid[MAXGRIDTEMP] = {
7
             // 3.0: Lat/Lon grid
8
         { 0, 19, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,-4,1,-4,-4,4,4,1} },
9
             // 3.1: Rotated Lat/Lon grid
10
         { 1, 22, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,-4,1,-4,-4,4,4,1,-4,4,4} },
11
             // 3.2: Stretched Lat/Lon grid
12
         { 2, 22, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,-4,-4,4,1,-4,-4,4} },
13
             // 3.3: Stretched & Rotated Lat/Lon grid
14
         { 3, 25, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,-4,-4,4,1,-4,4,4,-4,-4,4} },
15
// Added GDT 3.4,3.5    (08/05/2013)
16
             // 3.4: Variable resolution Latitude/Longitude
17
         { 4, 13, 1, {1,1,4,1,4,1,4,4,4,4,4,1,1} },
18
             // 3.5: Variable resolution rotate Latitude/Longitude
19
         { 5, 16, 1, {1,1,4,1,4,1,4,4,4,4,4,1,1,-4,4,4} },
20
             // 3.12: Transverse Mercator
21
         {12, 22, 0, {1,1,4,1,4,1,4,4,4,-4,4,1,-4,-4,-4,1,4,4,-4,-4,-4,-4} },
22
             // 3.101: General unstructured grid
23
         {101, 4, 0, {1,4,1,-4} },
24
             // 3.140: Lambert Azimuthal Equal Area Projection
25
         {140, 17, 0, {1,1,4,1,4,1,4,4,4,-4,-4,-4,-4,1,4,4,1} },
26
//
27
             // 3.10: Mercator
28
         {10, 19, 0, {1,1,4,1,4,1,4,4,4,-4,-4,1,-4,-4,-4,1,4,4,4} },
29
             // 3.20: Polar Stereographic Projection
30
         {20, 18, 0, {1,1,4,1,4,1,4,4,4,-4,-4,1,-4,-4,-4,4,1,1} },
31
             // 3.30: Lambert Conformal
32
         {30, 22, 0, {1,1,4,1,4,1,4,4,4,-4,4,1,-4,4,4,4,1,1,-4,-4,-4,4} },
33
             // 3.31: Albers equal area
34
         {31, 22, 0, {1,1,4,1,4,1,4,4,4,-4,4,1,-4,4,4,4,1,1,-4,-4,-4,4} },
35
             // 3.40: Gaussian Lat/Lon
36
         {40, 19, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1} },
37
             // 3.41: Rotated Gaussian Lat/Lon
38
         {41, 22, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1,-4,4,4} },
39
             // 3.42: Stretched Gaussian Lat/Lon
40
         {42, 22, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1,-4,4,-4} },
41
             // 3.43: Stretched and Rotated Gaussian Lat/Lon
42
         {43, 25, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1,-4,4,4,-4,4,-4} },
43
             // 3.50: Spherical Harmonic Coefficients
44
         {50, 5, 0, {4,4,4,1,1} },
45
             // 3.51: Rotated Spherical Harmonic Coefficients
46
         {51, 8, 0, {4,4,4,1,1,-4,4,4} },
47
             // 3.52: Stretched Spherical Harmonic Coefficients
48
         {52, 8, 0, {4,4,4,1,1,-4,4,-4} },
49
             // 3.53: Stretched and Rotated Spherical Harmonic Coefficients
50
         {53, 11, 0, {4,4,4,1,1,-4,4,4,-4,4,-4} },
51
             // 3.90: Space View Perspective or orthographic
52
         {90, 21, 0, {1,1,4,1,4,1,4,4,4,-4,4,1,4,4,4,4,1,4,4,4,4} },
53
             // 3.100: Triangular grid based on an icosahedron
54
         {100, 11, 0, {1,1,2,1,-4,4,4,1,1,1,4} },
55
             // 3.110: Equatorial Azimuthal equidistant
56
         {110, 16, 0, {1,1,4,1,4,1,4,4,4,-4,4,1,4,4,1,1} },
57
             // 3.120: Azimuth-range projection
58
         {120, 7, 1, {4,4,-4,4,4,4,1} },
59
             // 3.204: Curvilinear Orthogonal Grid
60
         {204, 19, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1} },
61
             // 3.32768: Rot Lat/Lon E-grid (Arakawa)
62
         {32768, 19, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1} },
63
             // 3.32769: Rot Lat/Lon Non-E Staggered grid (Arakawa)
64
         {32769, 21, 0, {1,1,4,1,4,1,4,4,4,4,4,-4,4,1,-4,4,4,4,1,4,4} },
65
             // 3.1000: Cross Section Grid
66
         {1000, 20, 1, {1,1,4,1,4,1,4,4,4,4,-4,4,1,4,4,1,2,1,1,2} },
67
             // 3.1100: Hovmoller Diagram Grid
68
         {1100, 28, 0, {1,1,4,1,4,1,4,4,4,4,-4,4,1,-4,4,1,4,1,-4,1,1,-4,2,1,1,1,1,1} },
69
             // 3.1200: Time Section Grid
70
         {1200, 16, 1, {4,1,-4,1,1,-4,2,1,1,1,1,1,2,1,1,2} }
71
72
      } ;
73
74
const struct gridtemplate *get_templatesgrid()
75
76
14.0k
{
77
14.0k
    return templatesgrid;
78
14.0k
}
79
80
g2int getgridindex(g2int number)
81
/*!$$$  SUBPROGRAM DOCUMENTATION BLOCK
82
!                .      .    .                                       .
83
! SUBPROGRAM:    getgridindex
84
!   PRGMMR: Gilbert         ORG: W/NP11    DATE: 2001-06-28
85
!
86
! ABSTRACT: This function returns the index of specified Grid
87
!   Definition Template 3.NN (NN=number) in array templates.
88
!
89
! PROGRAM HISTORY LOG:
90
! 2001-06-28  Gilbert
91
! 2007-08-16  Vuong     -  Added GDT 3.204  Curvilinear Orthogonal Grid
92
! 2008-07-08  Vuong     -  Added GDT 3.32768 Rotate Lat/Lon E-grid (Arakawa)
93
! 2009-01-14  Vuong     -  Changed structure name template to gtemplate
94
! 2010-05-11  Vuong     -  Added GDT 3.32769 Rotate Lat/Lon Non-E Staggered grid (Arakawa)
95
! 2013-08-06  Vuong     -  Added GDT 3.4,3.5,3.12,3.101,3.140
96
!
97
! USAGE:    index=getgridindex(number)
98
!   INPUT ARGUMENT LIST:
99
!     number   - NN, indicating the number of the Grid Definition
100
!                Template 3.NN that is being requested.
101
!
102
! RETURNS:  Index of GDT 3.NN in array templates, if template exists.
103
!           = -1, otherwise.
104
!
105
! REMARKS: None
106
!
107
! ATTRIBUTES:
108
!   LANGUAGE: C
109
!   MACHINE:  IBM SP
110
!
111
!$$$*/
112
27.3k
{
113
27.3k
           g2int j,l_getgridindex=-1;
114
115
133k
           for (j=0;j<MAXGRIDTEMP;j++) {
116
133k
              if (number == templatesgrid[j].template_num) {
117
27.3k
                 l_getgridindex=j;
118
27.3k
                 return(l_getgridindex);
119
27.3k
              }
120
133k
           }
121
122
11
           return(l_getgridindex);
123
27.3k
}
124
125
gtemplate *getgridtemplate(g2int number)
126
/*!$$$  SUBPROGRAM DOCUMENTATION BLOCK
127
!                .      .    .                                       .
128
! SUBPROGRAM:    getgridtemplate
129
!   PRGMMR: Gilbert         ORG: W/NP11    DATE: 2000-05-09
130
!
131
! ABSTRACT: This subroutine returns grid template information for a
132
!   specified Grid Definition Template 3.NN.
133
!   The number of entries in the template is returned along with a map
134
!   of the number of octets occupied by each entry.  Also, a flag is
135
!   returned to indicate whether the template would need to be extended.
136
!
137
! PROGRAM HISTORY LOG:
138
! 2000-05-09  Gilbert
139
! 2007-08-16  Vuong     -  Added GDT 3.204  Curvilinear Orthogonal Grid
140
! 2008-07-08  Vuong     -  Added GDT 3.32768 Rotate Lat/Lon E-grid (Arakawa)
141
! 2010-05-11  Vuong     -  Added GDT 3.32769 Rotate Lat/Lon Non-E Staggered grid (Arakawa)
142
! 2009-01-14  Vuong     -  Changed structure name template to gtemplate
143
!
144
! USAGE:    template *getgridtemplate(number)
145
!   INPUT ARGUMENT LIST:
146
!     number   - NN, indicating the number of the Grid Definition
147
!                Template 3.NN that is being requested.
148
!
149
!   RETURN VALUE:
150
!        - Pointer to the returned template struct.
151
!          Returns NULL pointer, if template not found.
152
!
153
! REMARKS: None
154
!
155
! ATTRIBUTES:
156
!   LANGUAGE: C
157
!   MACHINE:  IBM SP
158
!
159
!$$$*/
160
13.9k
{
161
13.9k
           g2int l_index;
162
13.9k
           gtemplate *new;
163
164
13.9k
           l_index=getgridindex(number);
165
166
13.9k
           if (l_index != -1) {
167
13.9k
              new=(gtemplate *)malloc(sizeof(gtemplate));
168
13.9k
              new->type=3;
169
13.9k
              new->num=templatesgrid[l_index].template_num;
170
13.9k
              new->maplen=templatesgrid[l_index].mapgridlen;
171
13.9k
              new->needext=templatesgrid[l_index].needext;
172
13.9k
              new->map=(g2int *)templatesgrid[l_index].mapgrid;
173
13.9k
              new->extlen=0;
174
13.9k
              new->ext=0;        //NULL
175
13.9k
              return(new);
176
13.9k
           }
177
11
           else {
178
11
             printf("getgridtemplate: GDT Template 3.%d not defined.\n",(int)number);
179
11
           }
180
181
11
         return(0);        //NULL
182
13.9k
}
183
184
185
gtemplate *extgridtemplate(g2int number,g2int *list)
186
/*!$$$  SUBPROGRAM DOCUMENTATION BLOCK
187
!                .      .    .                                       .
188
! SUBPROGRAM:    extgridtemplate
189
!   PRGMMR: Gilbert         ORG: W/NP11    DATE: 2000-05-09
190
!
191
! ABSTRACT: This subroutine generates the remaining octet map for a
192
!   given Grid Definition Template, if required.  Some Templates can
193
!   vary depending on data values given in an earlier part of the
194
!   Template, and it is necessary to know some of the earlier entry
195
!   values to generate the full octet map of the Template.
196
!
197
! PROGRAM HISTORY LOG:
198
! 2000-05-09  Gilbert
199
! 2008-07-08  Vuong     -  Added GDT 3.32768 Rotate Lat/Lon E-grid (Arakawa)
200
! 2009-01-14  Vuong     -  Changed structure name template to gtemplate
201
! 2010-05-11  Vuong     -  Added GDT 3.32769 Rotate Lat/Lon Non-E Staggered grid (Arakawa)
202
! 2013-08-06  Vuong     -  Added GDT 3.4,3.5,3.12,3.101,3.140
203
!
204
! USAGE:    CALL extgridtemplate(number,list)
205
!   INPUT ARGUMENT LIST:
206
!     number   - NN, indicating the number of the Grid Definition
207
!                Template 3.NN that is being requested.
208
!     list()   - The list of values for each entry in
209
!                the Grid Definition Template.
210
!
211
!   RETURN VALUE:
212
!        - Pointer to the returned template struct.
213
!          Returns NULL pointer, if template not found.
214
!
215
! ATTRIBUTES:
216
!   LANGUAGE: C
217
!   MACHINE:  IBM SP
218
!
219
!$$$*/
220
0
{
221
0
           gtemplate *new;
222
0
           g2int l_index,i;
223
224
0
           l_index=getgridindex(number);
225
0
           if (l_index == -1) return(0);
226
227
0
           new=getgridtemplate(number);
228
0
           if( new == NULL ) return(NULL);
229
230
0
           if ( ! new->needext ) return(new);
231
232
0
           if ( number == 120 ) {
233
              /* Not sure of the threshold, but 100000 looks to be large */
234
              /* enough */
235
0
              if( list[1] < 0 || list[1] > 100000 )
236
0
                return new;
237
0
              new->extlen=list[1]*2;
238
0
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
239
0
              for (i=0;i<new->extlen;i++) {
240
0
                 if ( i%2 == 0 ) {
241
0
                    new->ext[i]=2;
242
0
                 }
243
0
                 else {
244
0
                    new->ext[i]=-2;
245
0
                 }
246
0
              }
247
0
           }
248
#if 0
249
           /* Commented out by GDAL: memory leaks... */
250
           else if ( number == 4 ) {
251
              new->extlen=list[7];
252
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
253
              for (i=0;i<new->extlen;i++) {
254
                 new->ext[i]=4;
255
              }
256
              new->extlen=list[8];
257
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
258
              for (i=0;i<new->extlen;i++) {
259
                 new->ext[i]=-4;
260
              }
261
           }
262
           else if ( number == 5 ) {
263
              new->extlen=list[7];
264
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
265
              for (i=0;i<new->extlen;i++) {
266
                 new->ext[i]=4;
267
              }
268
              new->extlen=list[8];
269
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
270
              for (i=0;i<new->extlen;i++) {
271
                 new->ext[i]=-4;
272
              }
273
           }
274
#endif
275
0
           else if ( number == 1000 ) {
276
               /* Not sure of the threshold, but 100000 looks to be large */
277
              /* enough */
278
0
              if( list[19] < 0 || list[19] > 100000 )
279
0
                return new;
280
0
              new->extlen=list[19];
281
0
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
282
0
              for (i=0;i<new->extlen;i++) {
283
0
                 new->ext[i]=4;
284
0
              }
285
0
           }
286
0
           else if ( number == 1200 ) {
287
              /* Not sure of the threshold, but 100000 looks to be large */
288
              /* enough */
289
0
              if( list[15] < 0 || list[15] > 100000 )
290
0
                return new;
291
0
              new->extlen=list[15];
292
0
              new->ext=(g2int *)malloc(sizeof(g2int)*new->extlen);
293
0
              for (i=0;i<new->extlen;i++) {
294
0
                 new->ext[i]=4;
295
0
              }
296
0
           }
297
298
0
           return(new);
299
300
0
}