static int pack_long(grib_accessor* a, const long* val, size_t *len) { grib_accessor_element* self = (grib_accessor_element*)a; int ret = 0; size_t size=0; long* ar=NULL; grib_context* c=a->parent->h->context; if(*len < 1){ ret = GRIB_ARRAY_TOO_SMALL; return ret; } if((ret = grib_get_size(a->parent->h, self->array,&size)) != GRIB_SUCCESS) return ret; ar=grib_context_malloc_clear(c,size*sizeof(long)); if (!ar) { grib_context_log(c,GRIB_LOG_ERROR,"unable to allocate %d bytes",size*sizeof(long)); return GRIB_OUT_OF_MEMORY; } if((ret = grib_get_long_array_internal(a->parent->h, self->array,ar,&size)) != GRIB_SUCCESS) return ret; ar[self->element]=*val; if((ret = grib_set_long_array_internal(a->parent->h, self->array,ar,size)) != GRIB_SUCCESS) return ret; grib_context_free(c,ar); return ret; }
static int unpack_long(grib_accessor* a, long* val, size_t *len) { int ret=GRIB_SUCCESS; long ni=0,nj=0,plpresent=0; size_t plsize=0; long* pl; int i; grib_accessor_number_of_points* self = (grib_accessor_number_of_points*)a; grib_context* c=a->context; if((ret = grib_get_long_internal(grib_handle_of_accessor(a), self->ni,&ni)) != GRIB_SUCCESS) return ret; if((ret = grib_get_long_internal(grib_handle_of_accessor(a), self->nj,&nj)) != GRIB_SUCCESS) return ret; if(self->plpresent && ((ret = grib_get_long_internal(grib_handle_of_accessor(a), self->plpresent,&plpresent)) != GRIB_SUCCESS) ) return ret; if (nj == 0) return GRIB_GEOCALCULUS_PROBLEM; if (plpresent) { /*reduced*/ plsize=nj; pl=(long*)grib_context_malloc(c,sizeof(long)*plsize); grib_get_long_array_internal(grib_handle_of_accessor(a),self->pl,pl, &plsize); *val=0; for (i=0;i<plsize;i++) *val+=pl[i]; grib_context_free(c,pl); } else { /*regular*/ *val=ni*nj; } return ret; }
static int init(grib_iterator* iter,grib_handle* h,grib_arguments* args) { int ret=GRIB_SUCCESS,j; double lat_first=0,lon_first=0,lat_last=0,lon_last=0,d=0; double* lats; size_t plsize=0; int l=0; long* pl; long nj=0,order=0,ilon_first,ilon_last,i; long row_count=0; grib_context* c=h->context; grib_iterator_gaussian_reduced* self = (grib_iterator_gaussian_reduced*)iter; const char* slat_first = grib_arguments_get_name(h,args,self->carg++); const char* slon_first = grib_arguments_get_name(h,args,self->carg++); const char* slat_last = grib_arguments_get_name(h,args,self->carg++); const char* slon_last = grib_arguments_get_name(h,args,self->carg++); const char* sorder = grib_arguments_get_name(h,args,self->carg++); const char* spl = grib_arguments_get_name(h,args,self->carg++); const char* snj = grib_arguments_get_name(h,args,self->carg++); if((ret = grib_get_double_internal(h, slat_first,&lat_first)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slon_first,&lon_first)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slat_last,&lat_last)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slon_last,&lon_last)) != GRIB_SUCCESS) return ret; if((ret = grib_get_long_internal(h, sorder,&order)) != GRIB_SUCCESS) return ret; if((ret = grib_get_long_internal(h, snj,&nj)) != GRIB_SUCCESS) return ret; lats=(double*)grib_context_malloc(h->context,sizeof(double)*order*2); if((ret = grib_get_gaussian_latitudes(order, lats)) != GRIB_SUCCESS) return ret; if((ret = grib_get_size(h,spl,&plsize)) != GRIB_SUCCESS) return ret; pl=(long*)grib_context_malloc(c,sizeof(long)*plsize); grib_get_long_array_internal(h,spl,pl, &plsize); self->las = grib_context_malloc(h->context,iter->nv*sizeof(double)); self->los = grib_context_malloc(h->context,iter->nv*sizeof(double)); while (lon_last<0) lon_last+=360; while (lon_first<0) lon_first+=360; d=fabs(lats[0]-lats[1]); if ( (fabs(lat_first-lats[0]) >= d ) || (fabs(lat_last+lats[0]) >= d ) || lon_first != 0 || fabs(lon_last - (360.0-90.0/order)) > 90.0/order ) { /*sub area*/ /*find starting latitude */ while (fabs(lat_first-lats[l]) > d ) {l++;} iter->e=0; for (j=0;j<plsize;j++) { row_count=0; /*printf("lat=%g\n",lats[j+l]);*/ grib_get_reduced_row(pl[j],lon_first,lon_last, &row_count,&ilon_first,&ilon_last); if (ilon_first>ilon_last) ilon_first-=pl[j]; for (i=ilon_first;i<=ilon_last;i++) { self->los[iter->e]=((i)*360.0)/pl[j]; self->las[iter->e]=lats[j+l]; iter->e++; } } } else { /*global*/ iter->e=0; for (j=0;j<plsize;j++) { row_count=pl[j]; for (i=0;i<row_count;i++) { self->los[iter->e]=(i*360.0)/row_count; self->las[iter->e]=lats[j]; iter->e++; } } } iter->e = -1; grib_context_free(h->context,lats); grib_context_free(h->context,pl); return ret; }
static int init(grib_iterator* i,grib_handle* h,grib_arguments* args) { grib_iterator_latlon_reduced* self = (grib_iterator_latlon_reduced*)i; int ret = GRIB_SUCCESS; double laf; double lal; long nlats; double lof,tlof; double lol,dimin; long *pl; size_t plsize =0 ; long k,j,ii; long nlons,plmax; double jdirinc = 0; double idirinc = 0; double dlon=0; int islocal=0; long nlons2 =0; /* adjusted num of longitudes */ const char* latofirst = grib_arguments_get_name(h,args,self->carg++); const char* longoffirst = grib_arguments_get_name(h,args,self->carg++); const char* latoflast = grib_arguments_get_name(h,args,self->carg++); const char* longoflast = grib_arguments_get_name(h,args,self->carg++); const char* nlats_name = grib_arguments_get_name(h,args,self->carg++); const char* jdirec = grib_arguments_get_name(h,args,self->carg++); const char* plac = grib_arguments_get_name(h,args,self->carg++); if(( ret = grib_get_double_internal(h,latofirst, &laf))) return ret; if(( ret = grib_get_double_internal(h,longoffirst, &lof))) return ret; if(( ret = grib_get_double_internal(h,latoflast, &lal))) return ret; if(( ret = grib_get_double_internal(h,longoflast, &lol))) return ret; if(( ret = grib_get_long_internal(h,nlats_name,&nlats))) return ret; if(( ret = grib_get_double_internal(h,jdirec,&jdirinc))) return ret; plsize = nlats; pl = (long*)grib_context_malloc(h->context,plsize*sizeof(long)); grib_get_long_array_internal(h,plac,pl, &plsize); self->las = (double*)grib_context_malloc(h->context,i->nv*sizeof(double)); self->los = (double*)grib_context_malloc(h->context,i->nv*sizeof(double)); plmax=pl[0]; for (j=0;j<nlats;j++) if (plmax<pl[j]) plmax=pl[j]; dimin=360.0/plmax; if ( 360-fabs(lol-lof) < 2 * dimin ) {dlon=360; islocal=0;} else if (lol < lof) { /* handle something like 150 to -120 to treat as 150 to 240 */ /* so that dlon is 90 (not -270) */ dlon=lol + 360.0 - lof; islocal=1; } else {dlon=lol-lof; islocal=1;} if (laf>lal) jdirinc=-jdirinc; k=0; for (j=0;j<nlats;j++) { nlons=pl[j]; tlof=lof; nlons2 = nlons-islocal; /*Sometimes there are no points on a latitude! Protect against div by zero*/ if (nlons2<1) nlons2=1; idirinc=dlon/nlons2; for (ii=0;ii<nlons;ii++) { self->las[k]=laf; self->los[k]=tlof; tlof+=idirinc; k++; } laf+=jdirinc; } i->e = -1; grib_context_free(h->context,pl); return ret; }
int grib_init_accessor_from_handle(grib_loader* loader,grib_accessor* ga,grib_arguments* default_value) { grib_handle* h = (grib_handle*)loader->data; int ret = GRIB_SUCCESS; size_t len = 0; char* sval = NULL; unsigned char* uval = NULL; long* lval = NULL; double* dval = NULL; static int first = 1; static const char* missing = 0; const char* name = NULL; int k = 0; grib_handle *g; int e, pack_missing = 0; grib_context_log(h->context,GRIB_LOG_DEBUG, "XXXXX Copying %s", ga->name); if(default_value) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying: setting %s to default value", ga->name); grib_pack_expression(ga,grib_arguments_get_expression(h,default_value,0)); } if( (ga->flags & GRIB_ACCESSOR_FLAG_NO_COPY) || ((ga->flags & GRIB_ACCESSOR_FLAG_EDITION_SPECIFIC) && loader->changing_edition ) || (ga->flags & GRIB_ACCESSOR_FLAG_FUNCTION) || ( (ga->flags & GRIB_ACCESSOR_FLAG_READ_ONLY) && !(ga->flags & GRIB_ACCESSOR_FLAG_COPY_OK) ) ) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying %s ignored", ga->name); return GRIB_SUCCESS; } #if 0 if(h->values) if(copy_values(h,ga) == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying: setting %s to multi-set-value", ga->name); return GRIB_SUCCESS; } #endif #if 0 if(h->loader) h->loader->init_accessor(h->loader,ga,default_value); #else /* COMEBACK here this is needed if we reparse during reparse.... */ g = h; while(g) { if(g->values) { if(copy_values(g,ga) == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying: setting %s to multi-set-value", ga->name); return GRIB_SUCCESS; } } g = g->main; } #endif /* Check if the same name exists in the original message ... */ k = 0; while( (k < MAX_ACCESSOR_NAMES) && ((name = ga->all_names[k]) != NULL) && ((ret = grib_get_size(h,name,&len)) != GRIB_SUCCESS)) k++; if(ret != GRIB_SUCCESS) { name = ga->name; if(first) { missing = getenv("GRIB_PRINT_MISSING"); first = 0; } grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying [%s] failed: %s", name,grib_get_error_message(ret)); if(missing) { fprintf(stdout,"REPARSE: no value for %s",name); if(default_value) fprintf(stdout," (default value)"); fprintf(stdout,"\n"); } return GRIB_SUCCESS; } /* we copy also virtual keys*/ if(len == 0) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying %s failed, length is 0", name); return GRIB_SUCCESS; } if((ga->flags & GRIB_ACCESSOR_FLAG_CAN_BE_MISSING) && grib_is_missing(h,name,&e) && e == GRIB_SUCCESS && len == 1) { grib_pack_missing(ga); pack_missing = 1; } switch(grib_accessor_get_native_type(ga)) { case GRIB_TYPE_STRING: /* len = len > 1024 ? len : 1024; */ grib_get_string_length(h,name,&len); sval = (char*)grib_context_malloc(h->context,len); ret = grib_get_string_internal(h,name,sval,&len); if(ret == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying string %s to %s", sval, name); ret = grib_pack_string(ga,sval,&len); } grib_context_free(h->context,sval); break; case GRIB_TYPE_LONG: lval = (long*)grib_context_malloc(h->context,len*sizeof(long)); ret = grib_get_long_array_internal(h,name,lval,&len); if(ret == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying %d long(s) %d to %s", len, lval[0], name); if(ga->same) { ret = grib_set_long_array(ga->parent->h,ga->name,lval,len); /* Allow for lists to be resized */ if((ret == GRIB_WRONG_ARRAY_SIZE || ret == GRIB_ARRAY_TOO_SMALL) && loader->list_is_resized) ret = GRIB_SUCCESS; } else { /* See GRIB-492. This is NOT an ideal solution! */ if (*lval == GRIB_MISSING_LONG || pack_missing) { ; /* No checks needed */ } else { /* If we have just one key of type long which has one octet, then do not exceed maximum value */ const long num_octets = ga->length; if (len == 1 && num_octets == 1 && *lval > 255) { *lval = 0; /* Reset to a reasonable value */ } } ret = grib_pack_long(ga,lval,&len); } } grib_context_free(h->context,lval); break; case GRIB_TYPE_DOUBLE: dval = (double*)grib_context_malloc(h->context,len*sizeof(double)); ret = grib_get_double_array_internal(h,name,dval,&len); if(ret == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying %d double(s) %g to %s", len, dval[0], name); if(ga->same) { ret = grib_set_double_array(ga->parent->h,ga->name,dval,len); /* Allow for lists to be resized */ if((ret == GRIB_WRONG_ARRAY_SIZE || ret == GRIB_ARRAY_TOO_SMALL) && loader->list_is_resized) ret = GRIB_SUCCESS; } else ret = grib_pack_double(ga,dval,&len); } grib_context_free(h->context,dval); break; case GRIB_TYPE_BYTES: uval = (unsigned char*)grib_context_malloc(h->context,len*sizeof(char)); ret = grib_get_bytes_internal(h,name,uval,&len); if(ret == GRIB_SUCCESS) { grib_context_log(h->context,GRIB_LOG_DEBUG, "Copying %d byte(s) to %s", len, name); ret = grib_pack_bytes(ga,uval,&len); } grib_context_free(h->context,uval); break; case GRIB_TYPE_LABEL: break; default: grib_context_log(h->context,GRIB_LOG_ERROR, "Copying %s, cannot establish type %d [%s]" , name,grib_accessor_get_native_type(ga),ga->creator->cclass->name); break; } return ret; }
static int pack_double(grib_accessor* a, const double* val, size_t *len) { grib_accessor_data_apply_boustrophedonic* self = (grib_accessor_data_apply_boustrophedonic*)a; size_t plSize=0; long *pl=0; double *values=0; double *pvalues=0; double *pval=0; size_t valuesSize=0; long i,j; int ret; long numberOfPoints,numberOfRows,numberOfColumns; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfPoints,&numberOfPoints); if (ret) return ret; if(*len < numberOfPoints) { *len = numberOfPoints; return GRIB_ARRAY_TOO_SMALL; } valuesSize=numberOfPoints; values=(double*)grib_context_malloc_clear(a->context,sizeof(double)*numberOfPoints); pvalues=values; pval=(double*)val; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfRows,&numberOfRows); if (ret) return ret; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfColumns,&numberOfColumns); if (ret) return ret; if (grib_get_size(grib_handle_of_accessor(a),self->pl,&plSize) == GRIB_SUCCESS) { Assert(plSize==numberOfRows); pl=(long*)grib_context_malloc_clear(a->context,sizeof(long)*plSize); ret=grib_get_long_array_internal(grib_handle_of_accessor(a),self->pl,pl,&plSize); if (ret) return ret; for (j=0;j<numberOfRows;j++) { if (j%2) { pvalues+=pl[j]; for (i=0;i<pl[j] ;i++) { *(--pvalues)=*(pval++); } pvalues+=pl[j]; } else { for (i=0;i<pl[j];i++) *(pvalues++)=*(pval++); } } grib_context_free(a->context,pl); } else { for (j=0;j<numberOfRows;j++) { if (j%2) { pvalues+=numberOfColumns; for (i=0;i<numberOfColumns;i++) *(--pvalues)=*(pval++); pvalues+=numberOfColumns; } else { for (i=0;i<numberOfColumns;i++) *(pvalues++)=*(pval++); } } } ret=grib_set_double_array_internal(grib_handle_of_accessor(a),self->values,values,valuesSize); if (ret) return ret; grib_context_free(a->context,values); return ret; }
static int unpack_double(grib_accessor* a, double* val, size_t *len) { grib_accessor_data_apply_boustrophedonic* self = (grib_accessor_data_apply_boustrophedonic*)a; size_t plSize=0; long *pl=0; double *values=0; double *pvalues=0; double *pval=0; size_t valuesSize=0; long i,j; int ret; long numberOfPoints,numberOfRows,numberOfColumns; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfPoints,&numberOfPoints); if (ret) return ret; if(*len < numberOfPoints) { *len = numberOfPoints; return GRIB_ARRAY_TOO_SMALL; } ret=grib_get_size(grib_handle_of_accessor(a),self->values,&valuesSize); if (ret) return ret; /* constant field */ if (valuesSize==0) return 0; if (valuesSize!=numberOfPoints) { grib_context_log(a->context,GRIB_LOG_ERROR,"boustrophedonic ordering error: ( %s=%ld ) != (sizeOf(%s)=%ld)", self->numberOfPoints,numberOfPoints,self->values,(long)valuesSize); return GRIB_DECODING_ERROR; } values=(double*)grib_context_malloc_clear(a->context,sizeof(double)*numberOfPoints); ret=grib_get_double_array_internal(grib_handle_of_accessor(a),self->values,values,&valuesSize); if (ret) return ret; pvalues=values; pval=val; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfRows,&numberOfRows); if (ret) return ret; ret=grib_get_long_internal(grib_handle_of_accessor(a),self->numberOfColumns,&numberOfColumns); if (ret) return ret; if (grib_get_size(grib_handle_of_accessor(a),self->pl,&plSize) == GRIB_SUCCESS) { Assert(plSize==numberOfRows); pl=(long*)grib_context_malloc_clear(a->context,sizeof(long)*plSize); ret=grib_get_long_array_internal(grib_handle_of_accessor(a),self->pl,pl,&plSize); if (ret) return ret; for (j=0;j<numberOfRows;j++) { if (j%2) { pval+=pl[j]; for (i=0;i<pl[j];i++) *(pval--)=*(pvalues++); pval+=pl[j]; } else { for (i=0;i<pl[j];i++) *(pval++)=*(pvalues++); } } grib_context_free(a->context,pl); } else { for (j=0;j<numberOfRows;j++) { if (j%2) { pval+=numberOfColumns-1; for (i=0;i<numberOfColumns;i++) *(pval--)=*(pvalues++); pval+=numberOfColumns+1; } else { for (i=0;i<numberOfColumns;i++) *(pval++)=*(pvalues++); } } } grib_context_free(a->context,values); return GRIB_SUCCESS; }
static int unpack_double(grib_accessor* a, double* values, size_t *len) { grib_accessor_data_g1second_order_row_by_row_packing* self = (grib_accessor_data_g1second_order_row_by_row_packing*)a; int ret=0; long numberOfGroups,numberOfSecondOrderPackedValues; long* groupWidths=0; long* firstOrderValues=0; long* X=0; long numberOfRows,numberOfColumns; long *numbersPerRow; long pos=0; long widthOfFirstOrderValues=0; long jPointsAreConsecutive; unsigned char* buf = (unsigned char*)a->parent->h->buffer->data; long k,i,j,n,Ni,Nj; double reference_value; long binary_scale_factor; long decimal_scale_factor; double s,d; size_t groupWidthsSize=0; int bitmapPresent=0; size_t plSize=0; long* pl=0; buf += grib_byte_offset(a); if((ret=grib_get_long_internal(a->parent->h,self->numberOfGroups,&numberOfGroups)) != GRIB_SUCCESS) return ret; if((ret=grib_get_long_internal(a->parent->h,self->jPointsAreConsecutive,&jPointsAreConsecutive)) != GRIB_SUCCESS) return ret; if (self->bitmap) bitmapPresent=1; ret=grib_get_size(a->parent->h,self->pl,&plSize); if (ret==GRIB_SUCCESS) { pl=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*plSize); if((ret=grib_get_long_array(a->parent->h,self->pl,pl,&plSize)) != GRIB_SUCCESS) return ret; } if((ret=grib_get_long_internal(a->parent->h,self->Ni,&Ni)) != GRIB_SUCCESS) return ret; if((ret=grib_get_long_internal(a->parent->h,self->Nj,&Nj)) != GRIB_SUCCESS) return ret; if (jPointsAreConsecutive) { numberOfRows=Ni; numberOfColumns=Nj; } else { numberOfRows=Nj; numberOfColumns=Ni; } numbersPerRow=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*numberOfRows); if (bitmapPresent) { long *bitmap,*pbitmap; size_t numberOfPoints=Ni*Nj; if (plSize) { numberOfPoints=0; for (i=0;i<numberOfRows;i++) numberOfPoints+=pl[i]; } bitmap=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*numberOfPoints); pbitmap=bitmap; grib_get_long_array(a->parent->h,self->bitmap,bitmap,&numberOfPoints); if (plSize) { for (i=0;i<numberOfRows;i++) { for (j=0;j<pl[i];j++) { numbersPerRow[i]+=*(bitmap++); } } } else { for (i=0;i<numberOfRows;i++) { numbersPerRow[i]=0; for (j=0;j<Ni;j++) { numbersPerRow[i]+=*(bitmap++); } } } grib_context_free(a->parent->h->context,pbitmap); } else { if (plSize) { for (i=0;i<numberOfRows;i++) numbersPerRow[i]=pl[i]; } else { for (i=0;i<numberOfRows;i++) numbersPerRow[i]=numberOfColumns; } } if((ret=grib_get_long_internal(a->parent->h,self->widthOfFirstOrderValues,&widthOfFirstOrderValues)) != GRIB_SUCCESS) return ret; if((ret=grib_get_long_internal(a->parent->h,self->binary_scale_factor,&binary_scale_factor)) != GRIB_SUCCESS) return ret; if((ret=grib_get_long_internal(a->parent->h,self->decimal_scale_factor,&decimal_scale_factor)) != GRIB_SUCCESS) return ret; if((ret=grib_get_double_internal(a->parent->h,self->reference_value,&reference_value)) != GRIB_SUCCESS) return ret; if((ret=grib_get_long_internal(a->parent->h,self->numberOfSecondOrderPackedValues, &numberOfSecondOrderPackedValues)) != GRIB_SUCCESS) return ret; groupWidths=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*numberOfGroups); groupWidthsSize=numberOfGroups; if((ret=grib_get_long_array_internal(a->parent->h,self->groupWidths, groupWidths,&groupWidthsSize)) != GRIB_SUCCESS) return ret; firstOrderValues=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*numberOfGroups); grib_decode_long_array(buf,&pos,widthOfFirstOrderValues,numberOfGroups,firstOrderValues); pos = 8 * ( (pos + 7 ) / 8); X=grib_context_malloc_clear(a->parent->h->context,sizeof(long)*numberOfSecondOrderPackedValues); n=0; k=0; for (i=0; i<numberOfGroups; i++) { if (groupWidths[i]>0) { for (j=0;j<numbersPerRow[k];j++) { X[n]=grib_decode_unsigned_long(buf,&pos,groupWidths[i]); X[n]+=firstOrderValues[i]; n++; } } else { for (j=0;j<numbersPerRow[k];j++) { X[n]=firstOrderValues[i]; n++; } } k++; } s = grib_power(binary_scale_factor,2); d = grib_power(-decimal_scale_factor,10) ; for (i=0; i<n; i++) { values[i] = (double) (((X[i]*s)+reference_value)*d); } grib_context_free(a->parent->h->context,firstOrderValues); grib_context_free(a->parent->h->context,X); grib_context_free(a->parent->h->context,groupWidths); if (plSize) grib_context_free(a->parent->h->context,pl); return ret; }
static int init(grib_iterator* iter,grib_handle* h,grib_arguments* args) { int ret=GRIB_SUCCESS, j, is_global=0; double lat_first=0,lon_first=0,lat_last=0,lon_last=0; double angular_precision = 1.0/1000000.0; double* lats; size_t plsize=0; long* pl; long max_pl=0; long nj=0,order=0,ilon_first,ilon_last,i; long row_count=0; long editionNumber = 0; grib_context* c=h->context; grib_iterator_gaussian_reduced* self = (grib_iterator_gaussian_reduced*)iter; const char* slat_first = grib_arguments_get_name(h,args,self->carg++); const char* slon_first = grib_arguments_get_name(h,args,self->carg++); const char* slat_last = grib_arguments_get_name(h,args,self->carg++); const char* slon_last = grib_arguments_get_name(h,args,self->carg++); const char* sorder = grib_arguments_get_name(h,args,self->carg++); const char* spl = grib_arguments_get_name(h,args,self->carg++); const char* snj = grib_arguments_get_name(h,args,self->carg++); if((ret = grib_get_double_internal(h, slat_first,&lat_first)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slon_first,&lon_first)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slat_last,&lat_last)) != GRIB_SUCCESS) return ret; if((ret = grib_get_double_internal(h, slon_last,&lon_last)) != GRIB_SUCCESS) return ret; if((ret = grib_get_long_internal(h, sorder,&order)) != GRIB_SUCCESS) return ret; if((ret = grib_get_long_internal(h, snj,&nj)) != GRIB_SUCCESS) return ret; if (grib_get_long(h, "editionNumber", &editionNumber)==GRIB_SUCCESS) { if (editionNumber == 1) angular_precision = 1.0/1000; } lats=(double*)grib_context_malloc(h->context,sizeof(double)*order*2); if (!lats) return GRIB_OUT_OF_MEMORY; if((ret = grib_get_gaussian_latitudes(order, lats)) != GRIB_SUCCESS) return ret; if((ret = grib_get_size(h,spl,&plsize)) != GRIB_SUCCESS) return ret; Assert(plsize); pl=(long*)grib_context_malloc(c,sizeof(long)*plsize); if (!pl) return GRIB_OUT_OF_MEMORY; grib_get_long_array_internal(h,spl,pl, &plsize); self->las = (double*)grib_context_malloc(h->context,iter->nv*sizeof(double)); if (!self->las) return GRIB_OUT_OF_MEMORY; self->los = (double*)grib_context_malloc(h->context,iter->nv*sizeof(double)); if (!self->los) return GRIB_OUT_OF_MEMORY; while (lon_last<0) lon_last+=360; while (lon_first<0) lon_first+=360; /* Find the maximum element of "pl" array, do not assume it's 4*N! */ /* This could be an Octahedral Gaussian Grid */ max_pl = pl[0]; for (j=1; j<plsize; j++) { if (pl[j] > max_pl) max_pl = pl[j]; } is_global = is_gaussian_global(lat_first, lat_last, lon_first, lon_last, max_pl, lats, angular_precision); if ( !is_global ) { int l=0; /*sub area*/ /*find starting latitude */ const double d = fabs(lats[0] - lats[1]); while (fabs(lat_first-lats[l]) > d ) {l++;} iter->e=0; for (j=0;j<plsize;j++) { row_count=0; grib_get_reduced_row(pl[j],lon_first,lon_last, &row_count,&ilon_first,&ilon_last); if (ilon_first>ilon_last) ilon_first-=pl[j]; for (i=ilon_first;i<=ilon_last;i++) { #ifdef DEBUG Assert(iter->e < iter->nv); #endif self->los[iter->e]=((i)*360.0)/pl[j]; self->las[iter->e]=lats[j+l]; iter->e++; } } } else { /*global*/ iter->e=0; for (j=0;j<plsize;j++) { row_count=pl[j]; for (i=0;i<row_count;i++) { #ifdef DEBUG Assert(iter->e < iter->nv); #endif self->los[iter->e]=(i*360.0)/row_count; self->las[iter->e]=lats[j]; iter->e++; } } } iter->e = -1; grib_context_free(h->context,lats); grib_context_free(h->context,pl); return ret; }