Loading...
Searching...
No Matches
g2_unpack3.c
Go to the documentation of this file.
#include "grib2_int.h"
#include <stdio.h>
#include <stdlib.h>
g2int
g2_unpack3(unsigned char *cgrib, g2int *iofst, g2int **igds, g2int **igdstmpl,
g2int *mapgridlen, g2int **ideflist, g2int *idefnum)
{
g2int i, j, nbits, isecnum;
g2int lensec, ibyttem = 0, isign, newlen;
g2int *ligds, *ligdstmpl = NULL, *lideflist = NULL;
gtemplate *mapgrid;
*igds = NULL;
*igdstmpl = NULL;
*ideflist = NULL;
gbit(cgrib, &lensec, *iofst, 32); /* Get Length of Section */
*iofst = *iofst + 32;
gbit(cgrib, &isecnum, *iofst, 8); /* Get Section Number */
*iofst = *iofst + 8;
if (isecnum != 3)
{
*idefnum = 0;
*mapgridlen = 0;
return G2_UNPACK_BAD_SEC;
}
ligds = calloc(5, sizeof(g2int));
*igds = ligds;
gbit(cgrib, &ligds[0], *iofst, 8); /* Get source of Grid def. */
*iofst = *iofst + 8;
gbit(cgrib, &ligds[1], *iofst, 32); /* Get number of grid pts. */
*iofst = *iofst + 32;
gbit(cgrib, &ligds[2], *iofst, 8); /* Get num octets for opt. list */
*iofst = *iofst + 8;
gbit(cgrib, &ligds[3], *iofst, 8); /* Get interpret. for opt. list */
*iofst = *iofst + 8;
gbit(cgrib, &ligds[4], *iofst, 16); /* Get Grid Def Template num. */
*iofst = *iofst + 16;
if (ligds[4] != 65535)
{
/* Get Grid Definition Template */
if (!(mapgrid = getgridtemplate(ligds[4])))
{ /* undefined template */
free(ligds);
return G2_UNPACK3_BAD_GDT;
}
*mapgridlen = mapgrid->maplen;
/* Unpack each value into array igdstmpl from the the
* appropriate number of octets, which are specified in
* corresponding entries in array mapgrid. */
if (*mapgridlen > 0)
{
if (!(ligdstmpl = calloc(*mapgridlen, sizeof(g2int))))
{
*mapgridlen = 0;
*igdstmpl = NULL;
if (mapgrid)
free(mapgrid);
return G2_UNPACK_NO_MEM;
}
*igdstmpl = ligdstmpl;
}
ibyttem = 0;
for (i = 0; i < *mapgridlen; i++)
{
nbits = abs(mapgrid->map[i]) * 8;
if (mapgrid->map[i] >= 0)
{
gbit(cgrib, ligdstmpl + i, *iofst, nbits);
}
else
{
gbit(cgrib, &isign, *iofst, 1);
gbit(cgrib, ligdstmpl + i, *iofst + 1, nbits - 1);
if (isign == 1)
ligdstmpl[i] = -1 * ligdstmpl[i];
}
*iofst = *iofst + nbits;
ibyttem = ibyttem + abs(mapgrid->map[i]);
}
/* Check to see if the Grid Definition Template needs to be
* extended. The number of values in a specific template may
* vary depending on data specified in the "static" part of
* the gtemplate. */
if (mapgrid->needext == 1)
{
free(mapgrid);
mapgrid = extgridtemplate(ligds[4], ligdstmpl);
/* Unpack the rest of the Grid Definition Template */
newlen = mapgrid->maplen + mapgrid->extlen;
ligdstmpl = realloc(ligdstmpl, newlen * sizeof(g2int));
*igdstmpl = ligdstmpl;
j = 0;
for (i = *mapgridlen; i < newlen; i++)
{
nbits = abs(mapgrid->ext[j]) * 8;
if (mapgrid->ext[j] >= 0)
{
gbit(cgrib, ligdstmpl + i, *iofst, nbits);
}
else
{
gbit(cgrib, &isign, *iofst, 1);
gbit(cgrib, ligdstmpl + i, *iofst + 1, nbits - 1);
if (isign == 1)
ligdstmpl[i] = -1 * ligdstmpl[i];
}
*iofst = *iofst + nbits;
ibyttem = ibyttem + abs(mapgrid->ext[j]);
j++;
}
*mapgridlen = newlen;
}
if (mapgrid->ext)
free(mapgrid->ext);
if (mapgrid)
free(mapgrid);
}
else
{ /* No Grid Definition Template */
*mapgridlen = 0;
*igdstmpl = 0;
}
/* Unpack optional list of numbers defining number of points in
* each row or column, if included. This is used for non
* regular grids. */
if (ligds[2] != 0)
{
nbits = ligds[2] * 8;
*idefnum = (lensec - 14 - ibyttem) / ligds[2];
if (*idefnum > 0)
lideflist = calloc(*idefnum, sizeof(g2int));
if (!lideflist)
{
*idefnum = 0;
*ideflist = NULL;
return G2_UNPACK_NO_MEM;
}
*ideflist = lideflist;
gbits(cgrib, lideflist, *iofst, nbits, 0, *idefnum);
*iofst = *iofst + (nbits * *idefnum);
}
else
{
*idefnum = 0;
*ideflist = NULL;
}
return G2_NO_ERROR; /* End of Section 3 processing */
}
g2_unpack3
g2int g2_unpack3(unsigned char *cgrib, g2int *iofst, g2int **igds, g2int **igdstmpl, g2int *mapgridlen, g2int **ideflist, g2int *idefnum)
Unpack Section 3 (Grid Definition Section) of a GRIB2 message.
Definition g2_unpack3.c:62
gbit
void gbit(unsigned char *in, g2int *iout, g2int iskip, g2int nbits)
Get arbitrary size values from a packed bit string, right justifying each value in the unpacked iout ...
Definition gbits.c:20
gbits
void gbits(unsigned char *in, g2int *iout, g2int iskip, g2int nbits, g2int nskip, g2int n)
Unpack arbitrary size values from a packed bit string, right justifying each value in the unpacked io...
Definition gbits.c:57
G2_UNPACK_BAD_SEC
#define G2_UNPACK_BAD_SEC
Bad section number in unpacking function.
Definition grib2.h:457
G2_UNPACK_NO_MEM
#define G2_UNPACK_NO_MEM
Error allocating memory in unpack function.
Definition grib2.h:458
G2_NO_ERROR
#define G2_NO_ERROR
Function succeeded.
Definition grib2.h:431
G2_UNPACK3_BAD_GDT
#define G2_UNPACK3_BAD_GDT
In g2_unpack3(), undefined Grid Definition Template.
Definition grib2.h:459
g2int
int64_t g2int
Long integer type.
Definition grib2.h:32
grib2_int.h
Header file with internal function prototypes NCEPLIBS-g2c library.
gtemplate::ext
g2int * ext
Number of octets of each entry in the extension part of the template.
Definition grib2_int.h:302
gtemplate::extlen
g2int extlen
Number of entries in the template extension.
Definition grib2_int.h:298
gtemplate::map
g2int * map
Number of octets of each entry in the static part of the template.
Definition grib2_int.h:292
gtemplate::needext
g2int needext
Indicates whether or not the template needs to be extended.
Definition grib2_int.h:295
extgridtemplate
gtemplate * extgridtemplate(g2int number, g2int *list)
This subroutine generates the remaining octet map for a given Grid Definition Template,...
Definition gridtemplates.c:241
getgridtemplate
gtemplate * getgridtemplate(g2int number)
This subroutine returns grid template information for a specified Grid Definition Template for [Secti...
Definition gridtemplates.c:193
gtemplate::maplen
g2int maplen
Number of entries in the static part of the template.
Definition grib2_int.h:288
gtemplate
Struct for GRIB template, returned by getgridtemplate().
Definition grib2_int.h:278