LCOV - code coverage report
Current view: directory - frmts/grib/degrib18/g2clib-1.0.4 - g2_unpack4.c (source / functions) Found Hit Coverage
Test: gdal_filtered.info Lines: 77 43 55.8 %
Date: 2011-12-18 Functions: 1 1 100.0 %

       1                 : #include <stdio.h>
       2                 : #include <stdlib.h>
       3                 : #include "grib2.h"
       4                 : 
       5                 : 
       6               2 : g2int g2_unpack4(unsigned char *cgrib,g2int *iofst,g2int *ipdsnum,g2int **ipdstmpl,
       7                 :                g2int *mappdslen,g2float **coordlist,g2int *numcoord)
       8                 : ////$$$  SUBPROGRAM DOCUMENTATION BLOCK
       9                 : //                .      .    .                                       .
      10                 : // SUBPROGRAM:    g2_unpack4 
      11                 : //   PRGMMR: Gilbert         ORG: W/NP11    DATE: 2002-10-31
      12                 : //
      13                 : // ABSTRACT: This subroutine unpacks Section 4 (Product Definition Section)
      14                 : //           as defined in GRIB Edition 2.
      15                 : //
      16                 : // PROGRAM HISTORY LOG:
      17                 : // 2002-10-31  Gilbert
      18                 : //
      19                 : // USAGE:    int g2_unpack4(unsigned char *cgrib,g2int *iofst,g2int *ipdsnum,
      20                 : //                          g2int **ipdstmpl,g2int *mappdslen,
      21                 : //                          g2float **coordlist,g2int *numcoord)
      22                 : //   INPUT ARGUMENTS:
      23                 : //     cgrib    - Char array containing Section 4 of the GRIB2 message
      24                 : //     iofst    - Bit offset of the beginning of Section 4 in cgrib.
      25                 : //
      26                 : //   OUTPUT ARGUMENTS:      
      27                 : //     iofst    - Bit offset of the end of Section 4, returned.
      28                 : //     ipdsnum  - Product Definition Template Number ( see Code Table 4.0)
      29                 : //     ipdstmpl - Pointer to integer array containing the data values for 
      30                 : //                the specified Product Definition
      31                 : //                Template ( N=ipdsnum ).  Each element of this integer
      32                 : //                array contains an entry (in the order specified) of Product
      33                 : //                Defintion Template 4.N
      34                 : //     mappdslen- Number of elements in ipdstmpl[].  i.e. number of entries
      35                 : //                in Product Defintion Template 4.N  ( N=ipdsnum ).
      36                 : //     coordlist- Pointer to real array containing floating point values 
      37                 : //                intended to document
      38                 : //                the vertical discretisation associated to model data
      39                 : //                on hybrid coordinate vertical levels.  (part of Section 4)
      40                 : //     numcoord - number of values in array coordlist.
      41                 : //
      42                 : //   RETURN VALUES:
      43                 : //     ierr     - Error return code.
      44                 : //                0 = no error
      45                 : //                2 = Not section 4
      46                 : //                5 = "GRIB" message contains an undefined Product Definition
      47                 : //                    Template.
      48                 : //                6 = memory allocation error
      49                 : //
      50                 : // REMARKS: 
      51                 : //
      52                 : // ATTRIBUTES:
      53                 : //   LANGUAGE: C
      54                 : //   MACHINE:  
      55                 : //
      56                 : //$$$//
      57                 : {
      58                 : 
      59                 :       g2int ierr,needext,i,j,nbits,isecnum;
      60                 :       g2int lensec,isign,newlen;
      61                 :       g2int *coordieee;
      62               2 :       g2int *lipdstmpl=0;
      63                 :       g2float *lcoordlist;
      64                 :       xxtemplate *mappds;
      65                 : 
      66               2 :       ierr=0;
      67               2 :       *ipdstmpl=0;    // NULL
      68               2 :       *coordlist=0;    // NULL
      69                 : 
      70               2 :       gbit(cgrib,&lensec,*iofst,32);        // Get Length of Section
      71               2 :       *iofst=*iofst+32;
      72               2 :       gbit(cgrib,&isecnum,*iofst,8);         // Get Section Number
      73               2 :       *iofst=*iofst+8;
      74                 : 
      75               2 :       if ( isecnum != 4 ) {
      76               0 :          ierr=2;
      77               0 :          *numcoord=0;
      78               0 :          *mappdslen=0;
      79                 :         // fprintf(stderr,"g2_unpack4: Not Section 4 data.\n");
      80               0 :          return(ierr);
      81                 :       }
      82                 : 
      83               2 :       gbit(cgrib,numcoord,*iofst,16);    // Get num of coordinate values
      84               2 :       *iofst=*iofst+16;
      85               2 :       gbit(cgrib,ipdsnum,*iofst,16);    // Get Prod. Def Template num.
      86               2 :       *iofst=*iofst+16;
      87                 : 
      88                 :       //   Get Product Definition Template
      89               2 :       mappds=getpdstemplate(*ipdsnum);
      90               2 :       if (mappds == 0) {       // undefine template
      91               0 :         ierr=5;
      92               0 :         *mappdslen=0;
      93               0 :         return(ierr);
      94                 :       }
      95               2 :       *mappdslen=mappds->maplen;
      96               2 :       needext=mappds->needext;
      97                 :       //
      98                 :       //   Unpack each value into array ipdstmpl from the
      99                 :       //   the appropriate number of octets, which are specified in
     100                 :       //   corresponding entries in array mappds.
     101                 :       //
     102               2 :       if (*mappdslen > 0) lipdstmpl=(g2int *)calloc(*mappdslen,sizeof(g2int));
     103               2 :       if (lipdstmpl == 0) {
     104               0 :          ierr=6;
     105               0 :          *mappdslen=0;
     106               0 :          *ipdstmpl=0;     //NULL
     107               0 :          if ( mappds != 0 ) free(mappds);
     108               0 :          return(ierr);
     109                 :       }
     110                 :       else {
     111               2 :          *ipdstmpl=lipdstmpl;
     112                 :       }
     113              60 :       for (i=0;i<mappds->maplen;i++) {
     114              58 :         nbits=abs(mappds->map[i])*8;
     115              58 :         if ( mappds->map[i] >= 0 ) {
     116              50 :           gbit(cgrib,lipdstmpl+i,*iofst,nbits);
     117                 :         }
     118                 :         else {
     119               8 :           gbit(cgrib,&isign,*iofst,1);
     120               8 :           gbit(cgrib,lipdstmpl+i,*iofst+1,nbits-1);
     121               8 :           if (isign == 1) lipdstmpl[i]=-1*lipdstmpl[i];
     122                 :         }
     123              58 :         *iofst=*iofst+nbits;
     124                 :       }
     125                 :       //
     126                 :       //   Check to see if the Product Definition Template needs to be
     127                 :       //   extended.
     128                 :       //   The number of values in a specific template may vary
     129                 :       //   depending on data specified in the "static" part of the
     130                 :       //   template.
     131                 :       //
     132               2 :       if ( needext ==1 ) {
     133               2 :         free(mappds);
     134               2 :         mappds=extpdstemplate(*ipdsnum,lipdstmpl);
     135               2 :         newlen=mappds->maplen+mappds->extlen;
     136               2 :         lipdstmpl=(g2int *)realloc(lipdstmpl,newlen*sizeof(g2int));
     137               2 :         *ipdstmpl=lipdstmpl;
     138                 :         //   Unpack the rest of the Product Definition Template
     139               2 :         j=0;
     140               2 :         for (i=*mappdslen;i<newlen;i++) {
     141               0 :           nbits=abs(mappds->ext[j])*8;
     142               0 :           if ( mappds->ext[j] >= 0 ) {
     143               0 :             gbit(cgrib,lipdstmpl+i,*iofst,nbits);
     144                 :           }
     145                 :           else {
     146               0 :             gbit(cgrib,&isign,*iofst,1);
     147               0 :             gbit(cgrib,lipdstmpl+i,*iofst+1,nbits-1);
     148               0 :             if (isign == 1) lipdstmpl[i]=-1*lipdstmpl[i];
     149                 :           }
     150               0 :           *iofst=*iofst+nbits;
     151               0 :           j++;
     152                 :         }
     153               2 :         *mappdslen=newlen;
     154                 :       }
     155               2 :       if( mappds->ext != 0 ) free(mappds->ext);
     156               2 :       if( mappds != 0 ) free(mappds);
     157                 :       //
     158                 :       //   Get Optional list of vertical coordinate values
     159                 :       //   after the Product Definition Template, if necessary.
     160                 :       //
     161               2 :       *coordlist=0;    // NULL
     162               2 :       if ( *numcoord != 0 ) {
     163               0 :          coordieee=(g2int *)calloc(*numcoord,sizeof(g2int));
     164               0 :          lcoordlist=(g2float *)calloc(*numcoord,sizeof(g2float));
     165               0 :          if (coordieee == 0 || lcoordlist == 0) {
     166               0 :             ierr=6;
     167               0 :             *numcoord=0;
     168               0 :             *coordlist=0;    // NULL
     169               0 :             if( coordieee != 0 ) free(coordieee);
     170               0 :             if( lcoordlist != 0 ) free(lcoordlist);
     171               0 :             return(ierr);
     172                 :          }
     173                 :          else {
     174               0 :             *coordlist=lcoordlist;
     175                 :          }
     176               0 :         gbits(cgrib,coordieee,*iofst,32,0,*numcoord);
     177               0 :         rdieee(coordieee,*coordlist,*numcoord);
     178               0 :         free(coordieee);
     179               0 :         *iofst=*iofst+(32*(*numcoord));
     180                 :       }
     181                 :       
     182               2 :       return(ierr);    // End of Section 4 processing
     183                 : 
     184                 : }

Generated by: LCOV version 1.7