stream_grb.c 16.8 KB
Newer Older
1
#ifdef HAVE_CONFIG_H
2
#include "config.h"
Uwe Schulzweida's avatar
Uwe Schulzweida committed
3
4
5
#endif

#include "cdi.h"
6
#include "cdi_int.h"
Uwe Schulzweida's avatar
Uwe Schulzweida committed
7
#include "stream_cgribex.h"
8
#include "stream_grb.h"
Uwe Schulzweida's avatar
Uwe Schulzweida committed
9
#include "stream_gribapi.h"
Thomas Jahns's avatar
Thomas Jahns committed
10
#include "gribapi.h"
Uwe Schulzweida's avatar
Uwe Schulzweida committed
11
12
#include "file.h"
#include "cgribex.h"  /* gribZip gribGetZip gribGinfo */
13

14
15
16
17
18
19
20
21
int cdiDebugExt                        =  0;      //  Debug level for the KNMI extensions
#ifdef HIRLAM_EXTENSIONS
// *** RELATED to GRIB only ***
int cdiGribUseTimeRangeIndicator        = 0;       // normaly cdo looks in grib for attribute called "stepType"
                                                   // but NWP models such as Harmonie 37h1.2, use "timeRangeIndicator"
                                                   // where:  0: for instanteneous fields; 4: for accumulated fields
#endif // HIRLAM_EXTENSIONS

22
23

// Regarding operation to change parameter identification:
24
25
// change if cdiGribChangeParameterID.active
struct cdiGribParamChange cdiGribChangeParameterID;
26

27
// Used only for CDO module Selmulti
28
29
30
31
32
void streamGrbChangeParameterIdentification(int code, int ltype, int lev)
{
  // NOTE this is a "PROXY" function for gribapiChangeParameterIdentification();
  // This just sets the globals. There are probably better solutions to this.
  // The parameter change is done by function  gribapiChangeParameterIdentification() in stream_gribapi.c
33
34
35
36
37
38
  // Setting this control variable to true will cause calling fnc. gribapiChangeParameterIdentification later.
  // After grib attributes have been changed this variable goes to false.
  cdiGribChangeParameterID.active = true;
  cdiGribChangeParameterID.code = code;
  cdiGribChangeParameterID.ltype = ltype;
  cdiGribChangeParameterID.lev = lev;
39
}
40

41
42
43
44
45
46
47
48
49
struct cdiGribModeChange cdiGribChangeModeUvRelativeToGrid;

// Used only for CDO module WindTrans
void streamGrbChangeModeUvRelativeToGrid(int mode)
{
  cdiGribChangeModeUvRelativeToGrid.active = true;
  cdiGribChangeModeUvRelativeToGrid.mode = (mode > 0);
}

50
51
52
53
54
struct cdiGribScanModeChange cdiGribDataScanningMode;

void streamGrbDefDataScanningMode(int scanmode)
{
  cdiGribDataScanningMode.active = true;
55
  cdiGribDataScanningMode.value = scanmode;
56
57
58
59
}

int  streamGrbInqDataScanningMode(void)
{
60
  return cdiGribDataScanningMode.value;
61
62
}

63

64
65
66
67
68
69
int grib1ltypeToZaxisType(int grib_ltype)
{
  int zaxistype = ZAXIS_GENERIC;

  switch ( grib_ltype )
    {
70
71
72
73
74
75
76
77
    case GRIB1_LTYPE_SURFACE:            zaxistype = ZAXIS_SURFACE;                break;
    case GRIB1_LTYPE_CLOUD_BASE:         zaxistype = ZAXIS_CLOUD_BASE;             break;
    case GRIB1_LTYPE_CLOUD_TOP:          zaxistype = ZAXIS_CLOUD_TOP;              break;
    case GRIB1_LTYPE_ISOTHERM0:          zaxistype = ZAXIS_ISOTHERM_ZERO;          break;
    case GRIB1_LTYPE_TOA:                zaxistype = ZAXIS_TOA;                    break;
    case GRIB1_LTYPE_SEA_BOTTOM:         zaxistype = ZAXIS_SEA_BOTTOM;             break;
    case GRIB1_LTYPE_ATMOSPHERE:         zaxistype = ZAXIS_ATMOSPHERE;             break;
    case GRIB1_LTYPE_MEANSEA:            zaxistype = ZAXIS_MEANSEA;                break;
78
    case GRIB1_LTYPE_99:
79
    case GRIB1_LTYPE_ISOBARIC_PA:
80
81
82
    case GRIB1_LTYPE_ISOBARIC:           zaxistype = ZAXIS_PRESSURE;               break;
    case GRIB1_LTYPE_HEIGHT:             zaxistype = ZAXIS_HEIGHT;                 break;
    case GRIB1_LTYPE_ALTITUDE:           zaxistype = ZAXIS_ALTITUDE;	           break;
Deike Kleberg's avatar
Deike Kleberg committed
83
    case GRIB1_LTYPE_SIGMA:
84
    case GRIB1_LTYPE_SIGMA_LAYER:        zaxistype = ZAXIS_SIGMA;	           break;
85
    case GRIB1_LTYPE_HYBRID:
86
    case GRIB1_LTYPE_HYBRID_LAYER:       zaxistype = ZAXIS_HYBRID;	           break;
87
    case GRIB1_LTYPE_LANDDEPTH:
88
89
90
91
92
93
94
95
    case GRIB1_LTYPE_LANDDEPTH_LAYER:    zaxistype = ZAXIS_DEPTH_BELOW_LAND;       break;
    case GRIB1_LTYPE_ISENTROPIC:         zaxistype = ZAXIS_ISENTROPIC;             break;
    case GRIB1_LTYPE_SEADEPTH:           zaxistype = ZAXIS_DEPTH_BELOW_SEA;        break;
    case GRIB1_LTYPE_LAKE_BOTTOM:        zaxistype = ZAXIS_LAKE_BOTTOM;            break;
    case GRIB1_LTYPE_SEDIMENT_BOTTOM:    zaxistype = ZAXIS_SEDIMENT_BOTTOM;        break;
    case GRIB1_LTYPE_SEDIMENT_BOTTOM_TA: zaxistype = ZAXIS_SEDIMENT_BOTTOM_TA;     break;
    case GRIB1_LTYPE_SEDIMENT_BOTTOM_TW: zaxistype = ZAXIS_SEDIMENT_BOTTOM_TW;     break;
    case GRIB1_LTYPE_MIX_LAYER:          zaxistype = ZAXIS_MIX_LAYER;              break;
96
97
    }

98
  return zaxistype;
99
100
101
102
103
104
105
106
107
}


int grib2ltypeToZaxisType(int grib_ltype)
{
  int zaxistype = ZAXIS_GENERIC;

  switch ( grib_ltype )
    {
108
109
110
111
112
113
114
115
116
117
118
119
    case GRIB2_LTYPE_SURFACE:            zaxistype = ZAXIS_SURFACE;                break;
    case GRIB2_LTYPE_CLOUD_BASE:         zaxistype = ZAXIS_CLOUD_BASE;             break;
    case GRIB2_LTYPE_CLOUD_TOP:          zaxistype = ZAXIS_CLOUD_TOP;              break;
    case GRIB2_LTYPE_ISOTHERM0:          zaxistype = ZAXIS_ISOTHERM_ZERO;          break;
    case GRIB2_LTYPE_TOA:                zaxistype = ZAXIS_TOA;                    break;
    case GRIB2_LTYPE_SEA_BOTTOM:         zaxistype = ZAXIS_SEA_BOTTOM;             break;
    case GRIB2_LTYPE_ATMOSPHERE:         zaxistype = ZAXIS_ATMOSPHERE;             break;
    case GRIB2_LTYPE_MEANSEA:            zaxistype = ZAXIS_MEANSEA;                break;
    case GRIB2_LTYPE_ISOBARIC:           zaxistype = ZAXIS_PRESSURE;               break;
    case GRIB2_LTYPE_HEIGHT:             zaxistype = ZAXIS_HEIGHT;                 break;
    case GRIB2_LTYPE_ALTITUDE:           zaxistype = ZAXIS_ALTITUDE;               break;
    case GRIB2_LTYPE_SIGMA:              zaxistype = ZAXIS_SIGMA;                  break;
120
    case GRIB2_LTYPE_HYBRID:
121
 /* case GRIB2_LTYPE_HYBRID_LAYER: */    zaxistype = ZAXIS_HYBRID;                 break;
122
    case GRIB2_LTYPE_LANDDEPTH:
123
124
125
126
127
128
129
130
131
132
 /* case GRIB2_LTYPE_LANDDEPTH_LAYER: */ zaxistype = ZAXIS_DEPTH_BELOW_LAND;       break;
    case GRIB2_LTYPE_ISENTROPIC:         zaxistype = ZAXIS_ISENTROPIC;             break;
    case GRIB2_LTYPE_SNOW:               zaxistype = ZAXIS_SNOW;                   break;
    case GRIB2_LTYPE_SEADEPTH:           zaxistype = ZAXIS_DEPTH_BELOW_SEA;        break;
    case GRIB2_LTYPE_LAKE_BOTTOM:        zaxistype = ZAXIS_LAKE_BOTTOM;            break;
    case GRIB2_LTYPE_SEDIMENT_BOTTOM:    zaxistype = ZAXIS_SEDIMENT_BOTTOM;        break;
    case GRIB2_LTYPE_SEDIMENT_BOTTOM_TA: zaxistype = ZAXIS_SEDIMENT_BOTTOM_TA;     break;
    case GRIB2_LTYPE_SEDIMENT_BOTTOM_TW: zaxistype = ZAXIS_SEDIMENT_BOTTOM_TW;     break;
    case GRIB2_LTYPE_MIX_LAYER:          zaxistype = ZAXIS_MIX_LAYER;              break;
    case GRIB2_LTYPE_REFERENCE:          zaxistype = ZAXIS_REFERENCE;              break;
133
134
    }

135
  return zaxistype;
136
}
Uwe Schulzweida's avatar
Uwe Schulzweida committed
137

Uwe Schulzweida's avatar
Uwe Schulzweida committed
138

Uwe Schulzweida's avatar
Uwe Schulzweida committed
139
140
141
142
143
144
int zaxisTypeToGrib1ltype(int zaxistype)
{
  int grib_ltype = -1;

  switch (zaxistype)
    {
145
    case ZAXIS_SURFACE:               grib_ltype = GRIB1_LTYPE_SURFACE;            break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
146
147
148
149
    case ZAXIS_GENERIC:               grib_ltype = -1;                             break;
    case ZAXIS_HYBRID:                grib_ltype = -1;                             break;
    case ZAXIS_HYBRID_HALF:           grib_ltype = -1;                             break;
    case ZAXIS_PRESSURE:              grib_ltype = GRIB1_LTYPE_ISOBARIC;           break;
150
151
    case ZAXIS_HEIGHT:                grib_ltype = GRIB1_LTYPE_HEIGHT;             break;
    case ZAXIS_DEPTH_BELOW_SEA:       grib_ltype = GRIB1_LTYPE_SEADEPTH;           break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
152
    case ZAXIS_DEPTH_BELOW_LAND:      grib_ltype = GRIB1_LTYPE_LANDDEPTH;          break;
153
    case ZAXIS_ISENTROPIC:            grib_ltype = GRIB1_LTYPE_ISENTROPIC;         break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
154
155
156
157
158
159
160
    case ZAXIS_TRAJECTORY:            grib_ltype = -1;                             break;
    case ZAXIS_ALTITUDE:              grib_ltype = GRIB1_LTYPE_ALTITUDE;           break;
    case ZAXIS_SIGMA:                 grib_ltype = GRIB1_LTYPE_SIGMA;              break;
    case ZAXIS_MEANSEA:               grib_ltype = GRIB1_LTYPE_MEANSEA;            break;
    case ZAXIS_TOA:                   grib_ltype = GRIB1_LTYPE_TOA;                break;
    case ZAXIS_SEA_BOTTOM:            grib_ltype = GRIB1_LTYPE_SEA_BOTTOM;         break;
    case ZAXIS_ATMOSPHERE:            grib_ltype = GRIB1_LTYPE_ATMOSPHERE;         break;
161
162
163
    case ZAXIS_CLOUD_BASE:            grib_ltype = GRIB1_LTYPE_CLOUD_BASE;         break;
    case ZAXIS_CLOUD_TOP:             grib_ltype = GRIB1_LTYPE_CLOUD_TOP;          break;
    case ZAXIS_ISOTHERM_ZERO:         grib_ltype = GRIB1_LTYPE_ISOTHERM0;          break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
164
    case ZAXIS_SNOW:                  grib_ltype = -1;                             break;
165
166
167
168
169
    case ZAXIS_LAKE_BOTTOM:           grib_ltype = GRIB1_LTYPE_LAKE_BOTTOM;        break;
    case ZAXIS_SEDIMENT_BOTTOM:       grib_ltype = GRIB1_LTYPE_SEDIMENT_BOTTOM;    break;
    case ZAXIS_SEDIMENT_BOTTOM_TA:    grib_ltype = GRIB1_LTYPE_SEDIMENT_BOTTOM_TA; break;
    case ZAXIS_SEDIMENT_BOTTOM_TW:    grib_ltype = GRIB1_LTYPE_SEDIMENT_BOTTOM_TW; break;
    case ZAXIS_MIX_LAYER:             grib_ltype = GRIB1_LTYPE_MIX_LAYER;          break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
170
    case ZAXIS_REFERENCE:             grib_ltype = -1;                             break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
171
172
    }

173
  return grib_ltype;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
174
175
176
177
178
179
180
181
182
}


int zaxisTypeToGrib2ltype(int zaxistype)
{
  int grib_ltype = -1;

  switch (zaxistype)
    {
183
    case ZAXIS_SURFACE:               grib_ltype = GRIB2_LTYPE_SURFACE;            break;
184
185
186
187
    case ZAXIS_GENERIC:               grib_ltype = -1;                             break;
    case ZAXIS_HYBRID:                grib_ltype = GRIB2_LTYPE_HYBRID;             break;
    case ZAXIS_HYBRID_HALF:           grib_ltype = GRIB2_LTYPE_HYBRID;             break;
    case ZAXIS_PRESSURE:              grib_ltype = GRIB2_LTYPE_ISOBARIC;           break;
188
189
    case ZAXIS_HEIGHT:                grib_ltype = GRIB2_LTYPE_HEIGHT;             break;
    case ZAXIS_DEPTH_BELOW_SEA:       grib_ltype = GRIB2_LTYPE_SEADEPTH;           break;
190
    case ZAXIS_DEPTH_BELOW_LAND:      grib_ltype = GRIB2_LTYPE_LANDDEPTH;          break;
191
    case ZAXIS_ISENTROPIC:            grib_ltype = GRIB2_LTYPE_ISENTROPIC;         break;
192
193
194
195
196
197
198
    case ZAXIS_TRAJECTORY:            grib_ltype = -1;                             break;
    case ZAXIS_ALTITUDE:              grib_ltype = GRIB2_LTYPE_ALTITUDE;           break;
    case ZAXIS_SIGMA:                 grib_ltype = GRIB2_LTYPE_SIGMA;              break;
    case ZAXIS_MEANSEA:               grib_ltype = GRIB2_LTYPE_MEANSEA;            break;
    case ZAXIS_TOA:                   grib_ltype = GRIB2_LTYPE_TOA;                break;
    case ZAXIS_SEA_BOTTOM:            grib_ltype = GRIB2_LTYPE_SEA_BOTTOM;         break;
    case ZAXIS_ATMOSPHERE:            grib_ltype = GRIB2_LTYPE_ATMOSPHERE;         break;
199
200
201
    case ZAXIS_CLOUD_BASE:            grib_ltype = GRIB2_LTYPE_CLOUD_BASE;         break;
    case ZAXIS_CLOUD_TOP:             grib_ltype = GRIB2_LTYPE_CLOUD_TOP;          break;
    case ZAXIS_ISOTHERM_ZERO:         grib_ltype = GRIB2_LTYPE_ISOTHERM0;          break;
202
    case ZAXIS_SNOW:                  grib_ltype = GRIB2_LTYPE_SNOW;               break;
203
204
205
206
207
    case ZAXIS_LAKE_BOTTOM:           grib_ltype = GRIB2_LTYPE_LAKE_BOTTOM;        break;
    case ZAXIS_SEDIMENT_BOTTOM:       grib_ltype = GRIB2_LTYPE_SEDIMENT_BOTTOM;    break;
    case ZAXIS_SEDIMENT_BOTTOM_TA:    grib_ltype = GRIB2_LTYPE_SEDIMENT_BOTTOM_TA; break;
    case ZAXIS_SEDIMENT_BOTTOM_TW:    grib_ltype = GRIB2_LTYPE_SEDIMENT_BOTTOM_TW; break;
    case ZAXIS_MIX_LAYER:             grib_ltype = GRIB2_LTYPE_MIX_LAYER;          break;
208
    case ZAXIS_REFERENCE:             grib_ltype = GRIB2_LTYPE_REFERENCE;          break;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
209
210
    }

211
  return grib_ltype;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
212
213
214
}


Uwe Schulzweida's avatar
Uwe Schulzweida committed
215
216
217
218
int grbBitsPerValue(int datatype)
{
  int bitsPerValue = 16;

219
  if ( datatype == CDI_DATATYPE_CPX32 || datatype == CDI_DATATYPE_CPX64 )
220
    Error("CDI/GRIB library does not support complex numbers!");
Uwe Schulzweida's avatar
Uwe Schulzweida committed
221

Uwe Schulzweida's avatar
Uwe Schulzweida committed
222
223
224
225
  if ( datatype != CDI_UNDEFID )
    {
      if ( datatype > 0 && datatype <= 32 )
	bitsPerValue = datatype;
226
      else if ( datatype == CDI_DATATYPE_FLT64 )
Uwe Schulzweida's avatar
Uwe Schulzweida committed
227
228
229
230
231
	bitsPerValue = 24;
      else
	bitsPerValue = 16;
    }

232
  return bitsPerValue;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
233
234
235
}


Uwe Schulzweida's avatar
Uwe Schulzweida committed
236
/*
237
int grbInqRecord(stream_t * streamptr, int *varID, int *levelID)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
238
239
240
{
  int status;

241
  status = cgribexInqRecord(streamptr, varID, levelID);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
242
243
244

  return (status);
}
Uwe Schulzweida's avatar
Uwe Schulzweida committed
245
*/
Uwe Schulzweida's avatar
Uwe Schulzweida committed
246

247
void grbDefRecord(stream_t * streamptr)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
248
{
249
  UNUSED(streamptr);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
250
251
252
}

static
253
int grbScanTimestep1(stream_t * streamptr)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
254
{
255
  int status = CDI_EUFTYPE;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
256

257
#if  defined  (HAVE_LIBCGRIBEX)
258
259
  int filetype  = streamptr->filetype;

260
  if ( filetype == CDI_FILETYPE_GRB )
261
262
263
    status = cgribexScanTimestep1(streamptr);
#endif
#if defined(HAVE_LIBCGRIBEX) && defined (HAVE_LIBGRIB_API)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
264
  else
265
#endif
266
267
268
#ifdef HAVE_LIBGRIB_API
    status = gribapiScanTimestep1(streamptr);
#endif
269

270
  return status;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
271
272
273
}

static
274
int grbScanTimestep2(stream_t * streamptr)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
275
{
276
  int status = CDI_EUFTYPE;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
277

278
#if  defined  (HAVE_LIBCGRIBEX)
279
280
  int filetype = streamptr->filetype;

281
  if ( filetype == CDI_FILETYPE_GRB )
282
    status = cgribexScanTimestep2(streamptr);
283
284
#endif
#if defined(HAVE_LIBCGRIBEX) && defined (HAVE_LIBGRIB_API)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
285
  else
286
#endif
287
288
289
#ifdef HAVE_LIBGRIB_API
    status = gribapiScanTimestep2(streamptr);
#endif
Uwe Schulzweida's avatar
Uwe Schulzweida committed
290

291
  return status;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
292
293
294
}

static
295
int grbScanTimestep(stream_t * streamptr)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
296
{
297
  int status = CDI_EUFTYPE;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
298

299
#if  defined  (HAVE_LIBCGRIBEX)
300
301
  int filetype  = streamptr->filetype;

302
  if ( filetype == CDI_FILETYPE_GRB )
303
    status = cgribexScanTimestep(streamptr);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
304
  else
305
#endif
306
307
308
309
310
#ifdef HAVE_LIBGRIB_API
    status = gribapiScanTimestep(streamptr);
#else
    Error("Sufficient GRIB support unavailable!");
#endif
Uwe Schulzweida's avatar
Uwe Schulzweida committed
311

312
  return status;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
313
314
315
}


316
#if  defined  (HAVE_LIBGRIB)
317
int grbInqContents(stream_t * streamptr)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
318
319
320
{
  streamptr->curTsID = 0;

321
  int status = grbScanTimestep1(streamptr);
322
  if ( status == 0 && streamptr->ntsteps == -1 ) status = grbScanTimestep2(streamptr);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
323

324
  int fileID = streamptr->fileID;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
325
326
  fileSetPos(fileID, 0, SEEK_SET);

327
  return status;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
328
}
329
#endif
Uwe Schulzweida's avatar
Uwe Schulzweida committed
330

331
int grbInqTimestep(stream_t * streamptr, int tsID)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
332
333
{
  if ( tsID == 0 && streamptr->rtsteps == 0 )
334
    Error("Call to cdiInqContents missing!");
Uwe Schulzweida's avatar
Uwe Schulzweida committed
335
336

  if ( CDI_Debug )
337
    Message("tsid = %d rtsteps = %d", tsID, streamptr->rtsteps);
338

339
  int ntsteps = CDI_UNDEFID;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
340
341
  while ( (tsID + 1) > streamptr->rtsteps && ntsteps == CDI_UNDEFID )
    {
342
      ntsteps = grbScanTimestep(streamptr);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
343
344
345
346
347
348
349
      if ( ntsteps == CDI_EUFSTRUCT )
	{
	  streamptr->ntsteps = streamptr->rtsteps;
	  break;
	}
    }

350
351
  int nrecs;

Uwe Schulzweida's avatar
Uwe Schulzweida committed
352
353
354
355
356
357
358
359
360
361
  if ( tsID >= streamptr->ntsteps && streamptr->ntsteps != CDI_UNDEFID )
    {
      nrecs = 0;
    }
  else
    {
      streamptr->curTsID = tsID;
      nrecs = streamptr->tsteps[tsID].nrecs;
    }

362
  return nrecs;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
363
364
365
}


Uwe Schulzweida's avatar
Uwe Schulzweida committed
366
void streamInqGRIBinfo(int streamID, int *intnum, float *fltnum, off_t *bignum)
Uwe Schulzweida's avatar
Uwe Schulzweida committed
367
{
368
  stream_t *streamptr = stream_to_pointer(streamID);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
369

370
  int filetype = streamptr->filetype;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
371

372
  if ( filetype == CDI_FILETYPE_GRB )
Uwe Schulzweida's avatar
Uwe Schulzweida committed
373
    {
374
375
376
377
378
      int tsID     = streamptr->curTsID;
      int vrecID   = streamptr->tsteps[tsID].curRecID;
      int recID    = streamptr->tsteps[tsID].recIDs[vrecID];
      off_t recpos = streamptr->tsteps[tsID].records[recID].position;
      int zip      = streamptr->tsteps[tsID].records[recID].zip;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
379

380
381
      void *gribbuffer = streamptr->record->buffer;
      size_t gribbuffersize = streamptr->record->buffersize;
Uwe Schulzweida's avatar
Uwe Schulzweida committed
382
383

      if ( zip > 0 )
384
	Error("Compressed GRIB records unsupported!");
Uwe Schulzweida's avatar
Uwe Schulzweida committed
385
      else
Uwe Schulzweida's avatar
Uwe Schulzweida committed
386
        grib_info_for_grads(recpos, (long)gribbuffersize, (unsigned char *) gribbuffer, intnum, fltnum, bignum);
Uwe Schulzweida's avatar
Uwe Schulzweida committed
387
388
    }
}
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453


int grbGetGridtype(int gridID, size_t gridsize, bool *gridIsRotated, bool *gridIsCurvilinear)
{
  int gridtype = gridInqType(gridID);

  if ( gridtype == GRID_GENERIC )
    {
      int xsize = (int) gridInqXsize(gridID);
      int ysize = (int) gridInqYsize(gridID);

      if ( (ysize ==  32 || ysize ==  48 || ysize ==  64 ||
	    ysize ==  96 || ysize == 160 || ysize == 192 ||
	    ysize == 240 || ysize == 320 || ysize == 384 ||
	    ysize == 480 || ysize == 768 ) &&
	   (xsize == 2*ysize || xsize == 1) )
	{
	  gridtype = GRID_GAUSSIAN;
	}
      else if ( gridsize == 1 )
	{
	  gridtype = GRID_LONLAT;
	}
      else if ( gridInqXvals(gridID, NULL) && gridInqYvals(gridID, NULL) )
	{
	  gridtype = GRID_LONLAT;
	}
    }
  else if ( gridtype == GRID_CURVILINEAR )
    {
      int projID = gridInqProj(gridID);
      if ( projID != CDI_UNDEFID && gridInqType(projID) == GRID_PROJECTION )
        {
          gridID = projID;
          gridtype = GRID_PROJECTION;
        }
      else
        {
          static bool lwarning = true;
          if ( lwarning && gridsize > 1 )
            {
              lwarning = false;
              Warning("Curvilinear grid is unsupported in GRIB format! Created wrong Grid Description Section!");
            }
          *gridIsCurvilinear = true;
          gridtype = GRID_LONLAT;
        }
    }

  if ( gridtype == GRID_PROJECTION )
    {
      if ( gridInqProjType(gridID) == CDI_PROJ_RLL )
        {
          gridtype = GRID_LONLAT;
          *gridIsRotated = true;
        }
      else if ( gridInqProjType(gridID) == CDI_PROJ_LCC )
        {
          gridtype = GRID_LCC;
        }
    }

  return gridtype;
}

454
455
456
457
458
459
460
461
462
/*
 * Local Variables:
 * c-file-style: "Java"
 * c-basic-offset: 2
 * indent-tabs-mode: nil
 * show-trailing-whitespace: t
 * require-trailing-newline: t
 * End:
 */