Line data Source code
1 : /*****************************************************************************
2 : *
3 : * This module has a number of additions and improvements over the original
4 : * implementation to be suitable for usage in GDAL HDF driver.
5 : *
6 : * Andrey Kiselev <dron@ak4719.spb.edu> is responsible for all the changes.
7 : ****************************************************************************/
8 :
9 : /*
10 : Copyright (C) 1996 Hughes and Applied Research Corporation
11 :
12 : Permission to use, modify, and distribute this software and its documentation
13 : for any purpose without fee is hereby granted, provided that the above
14 : copyright notice appear in all copies and that both that copyright notice and
15 : this permission notice appear in supporting documentation.
16 : */
17 : /*****************************************************************************
18 : REVISIONS:
19 :
20 : Aug 31, 1999 Abe Taaheri Changed memory allocation for utility strings to
21 : the size of UTLSTR_MAX_SIZE.
22 : Added error check for memory unavailability in
23 : several functions.
24 : Added check for NULL metabuf returned from
25 : EHmeta... functions. NULL pointer returned from
26 : EHmeta... functions indicate that memory could not
27 : be allocated for metabuf.
28 : Jun 27, 2000 Abe Taaheri Added support for EASE grid that uses
29 : Behrmann Cylinderical Equal Area (BCEA) projection
30 : Oct 23, 2000 Abe Taaheri Updated for ISINUS projection, so that both codes
31 : 31 and 99 can be used for this projection.
32 : Jan 15, 2003 Abe Taaheri Modified for generalization of EASE Grid.
33 :
34 : Jun 05, 2003 Bruce Beaumont / Abe Taaheri
35 :
36 : Fixed SQUARE definition.
37 : Added static projection number/name translation
38 : Added projection table lookup in GDdefproj.
39 : Removed projection table from GDdefproj
40 : Added projection table lookup in GDprojinfo
41 : Removed projection table from GDprojinfo
42 : Added cast for compcode in call to SDsetcompress
43 : in GDdeffield to avoid compiler errors
44 : Removed declaration for unused variable endptr
45 : in GDSDfldsrch
46 : Removed initialization code for unused variables
47 : in GDSDfldsrch
48 : Removed declarations for unused variables
49 : BCEA_scale, r0, s0, xMtr0, xMtr1, yMtr0,
50 : and yMtr1 in GDll2ij
51 : Removed initialization code for unused variables
52 : in GDll2ij
53 : Added code in GEO projection handling to allow
54 : map to span dateline in GDll2ij
55 : Changed "for each point" loop in GDll2ij to
56 : return -2147483648.0 for xVal and yVal if
57 : for_trans returned an error instead of
58 : returning an error to the caller
59 : (Note: MAXLONG is defined as 2147483647.0 in
60 : function cproj.c of GCTP)
61 : Added code in GDij2ll to use for_trans to
62 : translate the BCEA corner points from packed
63 : degrees to meters
64 : Removed declarations for unused variables
65 : BCEA_scale, r0, s0, xMtr, yMtr, epsilon,
66 : beta, qp_cea, kz_cea, eccen, eccen_sq,
67 : phi1, sinphi1, cosphi1, lon, lat, xcor,
68 : ycor, and nlatlon from GDij2ll
69 : Removed initialization code for unused variables
70 : in GDij2ll
71 : Added declarations for xMtr0, yMtr0, xMtr1, and
72 : yMtr1 in GDij2ll
73 : Added special-case code for BCEA
74 : Changed "for each point" loop in GDij2ll to
75 : return PGSd_GCT_IN_ERROR (1.0e51) for
76 : longitude and latitude values if inv_trans
77 : returned an error instead of return an error
78 : to the caller
79 : Removed declaration for unused variable ii in
80 : GDgetpixvalues
81 : Removed declaration for unused variable
82 : numTileDims in GDtileinfo
83 : Added error message and error return at the
84 : end of GDll2mm_cea
85 : Added return statement to GDll2mm_cea
86 : ******************************************************************************/
87 : #include "cpl_string.h"
88 : #include "stdio.h"
89 : #include "mfhdf.h"
90 : #include "hcomp.h"
91 : #include <math.h>
92 : #include "HdfEosDef.h"
93 :
94 : #include "hdf4compat.h"
95 :
96 : extern void for_init(int32, int32, float64 *, int32, const char *, const char *, int32 *,
97 : int32 (*for_trans[])(double, double, double*, double*));
98 : extern void inv_init(int32, int32, float64 *, int32, const char *, const char *, int32 *,
99 : int32 (*inv_trans[])(double, double, double*, double*));
100 :
101 : #define GDIDOFFSET 4194304
102 : #define SQUARE(x) ((x) * (x)) /* x**2 */
103 :
104 :
105 : #define NGRID 200
106 : /* Grid Structure External Arrays */
107 : struct gridStructure
108 : {
109 : int32 active;
110 : int32 IDTable;
111 : int32 VIDTable[2];
112 : int32 fid;
113 : int32 nSDS;
114 : int32 *sdsID;
115 : int32 compcode;
116 : intn compparm[5];
117 : int32 tilecode;
118 : int32 tilerank;
119 : int32 tiledims[8];
120 : };
121 : static struct gridStructure GDXGrid[NGRID];
122 :
123 :
124 :
125 : #define NGRIDREGN 256
126 : struct gridRegion
127 : {
128 : int32 fid;
129 : int32 gridID;
130 : int32 xStart;
131 : int32 xCount;
132 : int32 yStart;
133 : int32 yCount;
134 : int32 somStart;
135 : int32 somCount;
136 : float64 upleftpt[2];
137 : float64 lowrightpt[2];
138 : int32 StartVertical[8];
139 : int32 StopVertical[8];
140 : char *DimNamePtr[8];
141 : };
142 : static struct gridRegion *GDXRegion[NGRIDREGN];
143 :
144 : /* define a macro for the string size of the utility strings and some dimension
145 : list strings. The value of 80 in the previous version of this code
146 : may not be enough in some cases. The length now is 512 which seems to
147 : be more than enough to hold larger strings. */
148 :
149 : #define UTLSTR_MAX_SIZE 512
150 :
151 : /* Static projection table */
152 : static const struct {
153 : int32 projcode;
154 : const char *projname;
155 : } Projections[] = {
156 : {GCTP_GEO, "GCTP_GEO"},
157 : {GCTP_UTM, "GCTP_UTM"},
158 : {GCTP_SPCS, "GCTP_SPCS"},
159 : {GCTP_ALBERS, "GCTP_ALBERS"},
160 : {GCTP_LAMCC, "GCTP_LAMCC"},
161 : {GCTP_MERCAT, "GCTP_MERCAT"},
162 : {GCTP_PS, "GCTP_PS"},
163 : {GCTP_POLYC, "GCTP_POLYC"},
164 : {GCTP_EQUIDC, "GCTP_EQUIDC"},
165 : {GCTP_TM, "GCTP_TM"},
166 : {GCTP_STEREO, "GCTP_STEREO"},
167 : {GCTP_LAMAZ, "GCTP_LAMAZ"},
168 : {GCTP_AZMEQD, "GCTP_AZMEQD"},
169 : {GCTP_GNOMON, "GCTP_GNOMON"},
170 : {GCTP_ORTHO, "GCTP_ORTHO"},
171 : {GCTP_GVNSP, "GCTP_GVNSP"},
172 : {GCTP_SNSOID, "GCTP_SNSOID"},
173 : {GCTP_EQRECT, "GCTP_EQRECT"},
174 : {GCTP_MILLER, "GCTP_MILLER"},
175 : {GCTP_VGRINT, "GCTP_VGRINT"},
176 : {GCTP_HOM, "GCTP_HOM"},
177 : {GCTP_ROBIN, "GCTP_ROBIN"},
178 : {GCTP_SOM, "GCTP_SOM"},
179 : {GCTP_ALASKA, "GCTP_ALASKA"},
180 : {GCTP_GOOD, "GCTP_GOOD"},
181 : {GCTP_MOLL, "GCTP_MOLL"},
182 : {GCTP_IMOLL, "GCTP_IMOLL"},
183 : {GCTP_HAMMER, "GCTP_HAMMER"},
184 : {GCTP_WAGIV, "GCTP_WAGIV"},
185 : {GCTP_WAGVII, "GCTP_WAGVII"},
186 : {GCTP_OBLEQA, "GCTP_OBLEQA"},
187 : {GCTP_ISINUS1, "GCTP_ISINUS1"},
188 : {GCTP_CEA, "GCTP_CEA"},
189 : {GCTP_BCEA, "GCTP_BCEA"},
190 : {GCTP_ISINUS, "GCTP_ISINUS"},
191 : {-1, NULL}
192 : };
193 :
194 : /* Compression Codes */
195 : static const char * const HDFcomp[] = {
196 : "HDFE_COMP_NONE",
197 : "HDFE_COMP_RLE",
198 : "HDFE_COMP_NBIT",
199 : "HDFE_COMP_SKPHUFF",
200 : "HDFE_COMP_DEFLATE"
201 : };
202 :
203 : /* Origin Codes */
204 : static const char * const originNames[] = {
205 : "HDFE_GD_UL",
206 : "HDFE_GD_UR",
207 : "HDFE_GD_LL",
208 : "HDFE_GD_LR"
209 : };
210 :
211 : /* Pixel Registration Codes */
212 : static const char * const pixregNames[] = {
213 : "HDFE_CENTER",
214 : "HDFE_CORNER"
215 : };
216 :
217 : /* Grid Function Prototypes (internal routines) */
218 : static intn GDchkgdid(int32, const char *, int32 *, int32 *, int32 *);
219 : static intn GDSDfldsrch(int32, int32, const char *, int32 *, int32 *,
220 : int32 *, int32 *, int32 [], int32 *);
221 : static intn GDwrrdfield(int32, const char *, const char *,
222 : int32 [], int32 [], int32 [], VOIDP datbuf);
223 : static intn GDwrrdattr(int32, const char *, int32, int32, const char *, VOIDP);
224 : static intn GDll2ij(int32, int32, float64 [], int32, int32, int32, float64[],
225 : float64[], int32, float64[], float64[], int32[], int32[],
226 : float64[], float64[]);
227 : static intn GDgetdefaults(int32, int32, float64[], int32,
228 : float64[], float64[]);
229 : static intn GDwrrdtile(int32, const char *, const char *, int32 [], VOIDP);
230 :
231 : /*----------------------------------------------------------------------------|
232 : | BEGIN_PROLOG |
233 : | |
234 : | FUNCTION: GDopen |
235 : | |
236 : | DESCRIPTION: Opens or creates HDF file in order to create, read, or write |
237 : | a grid. |
238 : | |
239 : | |
240 : | Return Value Type Units Description |
241 : | ============ ====== ========= ===================================== |
242 : | fid int32 HDF-EOS file ID |
243 : | |
244 : | INPUTS: |
245 : | filename char Filename |
246 : | l_access intn HDF l_access code |
247 : | |
248 : | |
249 : | OUTPUTS: |
250 : | None |
251 : | |
252 : | NOTES: |
253 : | |
254 : | |
255 : | Date Programmer Description |
256 : | ====== ============ ================================================= |
257 : | Jun 96 Joel Gales Original Programmer |
258 : | |
259 : | END_PROLOG |
260 : -----------------------------------------------------------------------------*/
261 : int32
262 20 : GDopen(const char *filename, intn l_access)
263 :
264 : {
265 : int32 fid /* HDF-EOS file ID */ ;
266 :
267 : /* Call EHopen to perform file l_access */
268 : /* ---------------------------------- */
269 20 : fid = EHopen(filename, l_access);
270 :
271 20 : return (fid);
272 :
273 : }
274 :
275 :
276 : /*----------------------------------------------------------------------------|
277 : | BEGIN_PROLOG |
278 : | |
279 : | FUNCTION: GDattach |
280 : | |
281 : | DESCRIPTION: Attaches to an existing grid within the file. |
282 : | |
283 : | |
284 : | Return Value Type Units Description |
285 : | ============ ====== ========= ===================================== |
286 : | gridID int32 grid structure ID |
287 : | |
288 : | INPUTS: |
289 : | fid int32 HDF-EOS file id |
290 : | gridname char grid structure name |
291 : | |
292 : | |
293 : | OUTPUTS: |
294 : | None |
295 : | |
296 : | NOTES: |
297 : | |
298 : | |
299 : | Date Programmer Description |
300 : | ====== ============ ================================================= |
301 : | Jun 96 Joel Gales Original Programmer |
302 : | Sep 99 Abe Taaheri Modified test for memory allocation check when no |
303 : | SDSs are in the grid, NCR24147 |
304 : | |
305 : | END_PROLOG |
306 : -----------------------------------------------------------------------------*/
307 : int32
308 7 : GDattach(int32 fid, const char *gridname)
309 :
310 : {
311 : intn i; /* Loop index */
312 : intn j; /* Loop index */
313 7 : intn ngridopen = 0; /* # of grid structures open */
314 : intn status; /* routine return status variable */
315 :
316 : uint8 acs; /* Read/Write file l_access code */
317 :
318 : int32 HDFfid; /* HDF file id */
319 : int32 vgRef; /* Vgroup reference number */
320 : int32 vgid[3]; /* Vgroup ID array */
321 7 : int32 gridID = -1;/* HDF-EOS grid ID */
322 : int32 *tags; /* Pnt to Vgroup object tags array */
323 : int32 *refs; /* Pnt to Vgroup object refs array */
324 : int32 dum; /* dummy variable */
325 : int32 sdInterfaceID; /* HDF SDS interface ID */
326 : int32 nObjects; /* # of objects in Vgroup */
327 : int32 nSDS; /* SDS counter */
328 : int32 l_index; /* SDS l_index */
329 : int32 sdid; /* SDS object ID */
330 7 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
331 :
332 : char name[80]; /* Vgroup name */
333 : char class[80]; /* Vgroup class */
334 : char errbuf[256];/* Buffer for error message */
335 : char acsCode[1]; /* Read/Write l_access char: "r/w" */
336 :
337 :
338 : /* Check HDF-EOS file ID, get back HDF file ID and l_access code */
339 : /* ----------------------------------------------------------- */
340 7 : status = EHchkfid(fid, gridname, &HDFfid, &dum, &acs);
341 :
342 :
343 7 : if (status == 0)
344 : {
345 : /* Convert numeric l_access code to character */
346 : /* ---------------------------------------- */
347 :
348 7 : acsCode[0] = (acs == 1) ? 'w' : 'r';
349 :
350 : /* Determine number of grids currently opened */
351 : /* ------------------------------------------- */
352 1407 : for (i = 0; i < NGRID; i++)
353 : {
354 1400 : ngridopen += GDXGrid[i].active;
355 : }
356 :
357 :
358 : /* If room for more ... */
359 : /* -------------------- */
360 7 : if (ngridopen < NGRID)
361 : {
362 :
363 : /* Search Vgroups for Grid */
364 : /* ------------------------ */
365 7 : vgRef = -1;
366 :
367 : while (1)
368 : {
369 37 : vgRef = Vgetid(HDFfid, vgRef);
370 :
371 : /* If no more Vgroups then exist while loop */
372 : /* ---------------------------------------- */
373 37 : if (vgRef == -1)
374 : {
375 0 : break;
376 : }
377 :
378 : /* Get name and class of Vgroup */
379 : /* ---------------------------- */
380 37 : vgid[0] = Vattach(HDFfid, vgRef, "r");
381 37 : VgetnameSafe(vgid[0], name, sizeof(name));
382 37 : Vgetclass(vgid[0], class);
383 :
384 :
385 : /*
386 : * If Vgroup with gridname and class GRID found, load tables
387 : */
388 :
389 37 : if (strcmp(name, gridname) == 0 &&
390 7 : strcmp(class, "GRID") == 0)
391 : {
392 : /* Attach to "Data Fields" and "Grid Attributes" Vgroups */
393 : /* ----------------------------------------------------- */
394 7 : tags = (int32 *) malloc(sizeof(int32) * 2);
395 7 : if(tags == NULL)
396 : {
397 0 : HEpush(DFE_NOSPACE,"GDattach", __FILE__, __LINE__);
398 0 : return(-1);
399 : }
400 7 : refs = (int32 *) malloc(sizeof(int32) * 2);
401 7 : if(refs == NULL)
402 : {
403 0 : HEpush(DFE_NOSPACE,"GDattach", __FILE__, __LINE__);
404 0 : free(tags);
405 0 : return(-1);
406 : }
407 7 : Vgettagrefs(vgid[0], tags, refs, 2);
408 7 : vgid[1] = Vattach(HDFfid, refs[0], acsCode);
409 7 : vgid[2] = Vattach(HDFfid, refs[1], acsCode);
410 7 : free(tags);
411 7 : free(refs);
412 :
413 :
414 : /* Setup External Arrays */
415 : /* --------------------- */
416 7 : for (i = 0; i < NGRID; i++)
417 : {
418 : /* Find empty entry in array */
419 : /* ------------------------- */
420 7 : if (GDXGrid[i].active == 0)
421 : {
422 : /*
423 : * Set gridID, Set grid entry active, Store root
424 : * Vgroup ID, Store sub Vgroup IDs, Store HDF-EOS
425 : * file ID
426 : */
427 7 : gridID = i + idOffset;
428 7 : GDXGrid[i].active = 1;
429 7 : GDXGrid[i].IDTable = vgid[0];
430 7 : GDXGrid[i].VIDTable[0] = vgid[1];
431 7 : GDXGrid[i].VIDTable[1] = vgid[2];
432 7 : GDXGrid[i].fid = fid;
433 7 : break;
434 : }
435 : }
436 :
437 : /* Get SDS interface ID */
438 : /* -------------------- */
439 7 : status = GDchkgdid(gridID, "GDattach", &dum,
440 : &sdInterfaceID, &dum);
441 7 : if( status < 0)
442 0 : return -1;
443 :
444 : /* Get # of entries within Data Vgroup & search for SDS */
445 : /* ---------------------------------------------------- */
446 7 : nObjects = Vntagrefs(vgid[1]);
447 :
448 7 : if (nObjects > 0)
449 : {
450 : /* Get tag and ref # for Data Vgroup objects */
451 : /* ----------------------------------------- */
452 3 : tags = (int32 *) malloc(sizeof(int32) * nObjects);
453 3 : if(tags == NULL)
454 : {
455 0 : HEpush(DFE_NOSPACE,"GDattach", __FILE__, __LINE__);
456 0 : return(-1);
457 : }
458 3 : refs = (int32 *) malloc(sizeof(int32) * nObjects);
459 3 : if(refs == NULL)
460 : {
461 0 : HEpush(DFE_NOSPACE,"GDattach", __FILE__, __LINE__);
462 0 : free(tags);
463 0 : return(-1);
464 : }
465 3 : Vgettagrefs(vgid[1], tags, refs, nObjects);
466 :
467 : /* Count number of SDS & allocate SDS ID array */
468 : /* ------------------------------------------- */
469 3 : nSDS = 0;
470 6 : for (j = 0; j < nObjects; j++)
471 : {
472 3 : if (tags[j] == DFTAG_NDG)
473 : {
474 3 : nSDS++;
475 : }
476 : }
477 3 : GDXGrid[i].sdsID = (int32 *) calloc(nSDS, 4);
478 3 : if(GDXGrid[i].sdsID == NULL && nSDS != 0)
479 : {
480 0 : HEpush(DFE_NOSPACE,"GDattach", __FILE__, __LINE__);
481 0 : free(tags);
482 0 : free(refs);
483 0 : return(-1);
484 : }
485 3 : nSDS = 0;
486 :
487 :
488 :
489 : /* Fill SDS ID array */
490 : /* ----------------- */
491 6 : for (j = 0; j < nObjects; j++)
492 : {
493 : /* If object is SDS then get id */
494 : /* ---------------------------- */
495 3 : if (tags[j] == DFTAG_NDG)
496 : {
497 3 : l_index = SDreftoindex(sdInterfaceID, refs[j]);
498 3 : sdid = SDselect(sdInterfaceID, l_index);
499 3 : GDXGrid[i].sdsID[nSDS] = sdid;
500 3 : nSDS++;
501 3 : GDXGrid[i].nSDS++;
502 : }
503 : }
504 3 : free(tags);
505 3 : free(refs);
506 : }
507 7 : break;
508 : }
509 :
510 : /* Detach Vgroup if not desired Grid */
511 : /* --------------------------------- */
512 30 : Vdetach(vgid[0]);
513 : }
514 :
515 : /* If Grid not found then set up error message */
516 : /* ------------------------------------------- */
517 7 : if (gridID == -1)
518 : {
519 0 : HEpush(DFE_RANGE, "GDattach", __FILE__, __LINE__);
520 0 : HEreport("Grid: \"%s\" does not exist within HDF file.\n",
521 : gridname);
522 : }
523 : }
524 : else
525 : {
526 : /* Too many files opened */
527 : /* --------------------- */
528 0 : gridID = -1;
529 0 : strcpy(errbuf,
530 : "No more than %d grids may be open simultaneously");
531 0 : strcat(errbuf, " (%s)");
532 0 : HEpush(DFE_DENIED, "GDattach", __FILE__, __LINE__);
533 0 : HEreport(errbuf, NGRID, gridname);
534 : }
535 :
536 : }
537 7 : return (gridID);
538 : }
539 :
540 :
541 : /*----------------------------------------------------------------------------|
542 : | BEGIN_PROLOG |
543 : | |
544 : | FUNCTION: GDchkgdid |
545 : | |
546 : | DESCRIPTION: |
547 : | |
548 : | |
549 : | Return Value Type Units Description |
550 : | ============ ====== ========= ===================================== |
551 : | status intn return status (0) SUCCEED, (-1) FAIL |
552 : | |
553 : | INPUTS: |
554 : | gridID int32 grid structure ID |
555 : | routname char Name of routine calling GDchkgdid |
556 : | |
557 : | OUTPUTS: |
558 : | fid int32 File ID |
559 : | sdInterfaceID int32 SDS interface ID |
560 : | gdVgrpID int32 grid Vgroup ID |
561 : | |
562 : | |
563 : | OUTPUTS: |
564 : | None |
565 : | |
566 : | NOTES: |
567 : | |
568 : | |
569 : | Date Programmer Description |
570 : | ====== ============ ================================================= |
571 : | Jun 96 Joel Gales Original Programmer |
572 : | |
573 : | END_PROLOG |
574 : -----------------------------------------------------------------------------*/
575 : static intn
576 219 : GDchkgdid(int32 gridID, const char *routname,
577 : int32 * fid, int32 * sdInterfaceID, int32 * gdVgrpID)
578 : {
579 219 : intn status = 0; /* routine return status variable */
580 : uint8 l_access; /* Read/Write l_access code */
581 : int32 gID; /* Grid ID - offset */
582 :
583 219 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
584 :
585 : static const char message1[] =
586 : "Invalid grid id: %d in routine \"%s\". ID must be >= %d and < %d.\n";
587 : static const char message2[] =
588 : "Grid id %d in routine \"%s\" not active.\n";
589 :
590 :
591 :
592 : /* Check for valid grid id */
593 :
594 219 : if (gridID < idOffset || gridID >= NGRID + idOffset)
595 : {
596 0 : status = -1;
597 0 : HEpush(DFE_RANGE, "GDchkgdid", __FILE__, __LINE__);
598 0 : HEreport(message1, gridID, routname, idOffset, NGRID + idOffset);
599 : }
600 : else
601 : {
602 :
603 : /* Compute "reduced" ID */
604 : /* -------------------- */
605 219 : gID = gridID % idOffset;
606 :
607 : /* Check for active grid ID */
608 : /* ------------------------ */
609 219 : if (GDXGrid[gID].active == 0)
610 : {
611 1 : status = -1;
612 1 : HEpush(DFE_GENAPP, "GDchkgdid", __FILE__, __LINE__);
613 1 : HEreport(message2, gridID, routname);
614 : }
615 : else
616 : {
617 :
618 : /* Get file & SDS ids and Grid key */
619 : /* -------------------------------- */
620 218 : status = EHchkfid(GDXGrid[gID].fid, " ",
621 : fid, sdInterfaceID, &l_access);
622 218 : *gdVgrpID = GDXGrid[gID].IDTable;
623 : }
624 : }
625 219 : return (status);
626 :
627 : }
628 :
629 :
630 : /*----------------------------------------------------------------------------|
631 : | BEGIN_PROLOG |
632 : | |
633 : | FUNCTION: GDdiminfo |
634 : | |
635 : | DESCRIPTION: Retrieve size of specified dimension. |
636 : | |
637 : | |
638 : | Return Value Type Units Description |
639 : | ============ ====== ========= ===================================== |
640 : | size int32 Size of dimension |
641 : | |
642 : | INPUTS: |
643 : | gridID int32 grid structure id |
644 : | dimname char Dimension name |
645 : | |
646 : | |
647 : | OUTPUTS: |
648 : | None |
649 : | |
650 : | NOTES: |
651 : | |
652 : | |
653 : | Date Programmer Description |
654 : | ====== ============ ================================================= |
655 : | Jun 96 Joel Gales Original Programmer |
656 : | Aug 96 Joel Gales Make metadata ODL compliant |
657 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
658 : | |
659 : | END_PROLOG |
660 : -----------------------------------------------------------------------------*/
661 : int32
662 4 : GDdiminfo(int32 gridID, const char *dimname)
663 :
664 : {
665 : intn status; /* routine return status variable */
666 :
667 : int32 fid; /* HDF-EOS file ID */
668 : int32 sdInterfaceID; /* HDF SDS interface ID */
669 : int32 gdVgrpID; /* Grid root Vgroup ID */
670 : int32 size; /* Dimension size */
671 4 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
672 :
673 :
674 : char *metabuf; /* Pointer to structural metadata (SM) */
675 : char *metaptrs[2];/* Pointers to begin and end of SM section */
676 : char gridname[80]; /* Grid Name */
677 : char *utlstr; /* Utility string */
678 :
679 : /* Allocate space for utility string */
680 : /* --------------------------------- */
681 4 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
682 4 : if(utlstr == NULL)
683 : {
684 0 : HEpush(DFE_NOSPACE,"GDdiminfo", __FILE__, __LINE__);
685 0 : return(-1);
686 : }
687 : /* Initialize return value */
688 : /* ----------------------- */
689 4 : size = -1;
690 :
691 :
692 : /* Check Grid ID */
693 : /* ------------- */
694 4 : status = GDchkgdid(gridID, "GDdiminfo", &fid, &sdInterfaceID, &gdVgrpID);
695 :
696 :
697 4 : if (status == 0)
698 : {
699 : /* Get grid name */
700 : /* ------------- */
701 4 : int gID = gridID % idOffset;
702 4 : if (gID >= NGRID)
703 : {
704 0 : free(utlstr);
705 0 : return -1;
706 : }
707 4 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
708 :
709 :
710 : /* Get pointers to "Dimension" section within SM */
711 : /* --------------------------------------------- */
712 4 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
713 : "Dimension", metaptrs);
714 :
715 4 : if(metabuf == NULL)
716 : {
717 0 : free(utlstr);
718 0 : return(-1);
719 : }
720 :
721 : /* Search for dimension name (surrounded by quotes) */
722 : /* ------------------------------------------------ */
723 4 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "\"", dimname, "\"\n");
724 4 : metaptrs[0] = strstr(metaptrs[0], utlstr);
725 :
726 : /*
727 : * If dimension found within grid structure then get dimension value
728 : */
729 4 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
730 : {
731 : /* Set endptr at end of dimension definition entry */
732 : /* ----------------------------------------------- */
733 4 : metaptrs[1] = strstr(metaptrs[0], "\t\t\tEND_OBJECT");
734 :
735 4 : status = EHgetmetavalue(metaptrs, "Size", utlstr);
736 :
737 4 : if (status == 0)
738 : {
739 4 : size = atoi(utlstr);
740 : }
741 : else
742 : {
743 0 : HEpush(DFE_GENAPP, "GDdiminfo", __FILE__, __LINE__);
744 0 : HEreport("\"Size\" string not found in metadata.\n");
745 : }
746 : }
747 : else
748 : {
749 0 : HEpush(DFE_GENAPP, "GDdiminfo", __FILE__, __LINE__);
750 0 : HEreport("Dimension \"%s\" not found.\n", dimname);
751 : }
752 :
753 4 : free(metabuf);
754 : }
755 4 : free(utlstr);
756 4 : return (size);
757 : }
758 :
759 :
760 :
761 :
762 :
763 : /*----------------------------------------------------------------------------|
764 : | BEGIN_PROLOG |
765 : | |
766 : | FUNCTION: GDgridinfo |
767 : | |
768 : | DESCRIPTION: Returns xdim, ydim and location of upper left and lower |
769 : | right corners, in meters. |
770 : | |
771 : | |
772 : | Return Value Type Units Description |
773 : | ============ ====== ========= ===================================== |
774 : | status intn return status (0) SUCCEED, (-1) FAIL |
775 : | |
776 : | INPUTS: |
777 : | fid int32 File ID |
778 : | gridname char Grid structure name |
779 : | |
780 : | OUTPUTS: |
781 : | xdimsize int32 Number of columns in grid |
782 : | ydimsize int32 Number of rows in grid |
783 : | upleftpt float64 Location (m/deg) of upper left corner |
784 : | lowrightpt float64 Location (m/deg) of lower right corner |
785 : | |
786 : | NOTES: |
787 : | |
788 : | |
789 : | Date Programmer Description |
790 : | ====== ============ ================================================= |
791 : | Jun 96 Joel Gales Original Programmer |
792 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
793 : | |
794 : | END_PROLOG |
795 : -----------------------------------------------------------------------------*/
796 : intn
797 11 : GDgridinfo(int32 gridID, int32 * xdimsize, int32 * ydimsize,
798 : float64 upleftpt[], float64 lowrightpt[])
799 :
800 : {
801 11 : intn status = 0; /* routine return status variable */
802 11 : intn statmeta = 0; /* EHgetmetavalue return status */
803 :
804 : int32 fid; /* HDF-EOS file ID */
805 : int32 sdInterfaceID; /* HDF SDS interface ID */
806 : int32 gdVgrpID; /* Grid root Vgroup ID */
807 11 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
808 :
809 :
810 : char *metabuf; /* Pointer to structural metadata (SM) */
811 : char *metaptrs[2];/* Pointers to begin and end of SM section */
812 : char gridname[80]; /* Grid Name */
813 : char *utlstr; /* Utility string */
814 :
815 : /* Allocate space for utility string */
816 : /* --------------------------------- */
817 11 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
818 11 : if(utlstr == NULL)
819 : {
820 0 : HEpush(DFE_NOSPACE,"GDgridinfo", __FILE__, __LINE__);
821 0 : return(-1);
822 : }
823 : /* Check Grid ID */
824 : /* ------------- */
825 11 : status = GDchkgdid(gridID, "GDgridinfo", &fid, &sdInterfaceID, &gdVgrpID);
826 :
827 11 : if (status == 0)
828 : {
829 : /* Get grid name */
830 : /* ------------- */
831 11 : int gID = gridID % idOffset;
832 11 : if (gID >= NGRID)
833 : {
834 0 : free(utlstr);
835 0 : return -1;
836 : }
837 11 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
838 :
839 :
840 : /* Get pointers to grid structure section within SM */
841 : /* ------------------------------------------------ */
842 11 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
843 : NULL, metaptrs);
844 :
845 11 : if(metabuf == NULL)
846 : {
847 0 : free(utlstr);
848 0 : return(-1);
849 : }
850 :
851 :
852 : /* Get xdimsize if requested */
853 : /* ------------------------- */
854 11 : if (xdimsize != NULL)
855 : {
856 11 : statmeta = EHgetmetavalue(metaptrs, "XDim", utlstr);
857 11 : if (statmeta == 0)
858 : {
859 11 : *xdimsize = atoi(utlstr);
860 : }
861 : else
862 : {
863 0 : status = -1;
864 0 : HEpush(DFE_GENAPP, "GDgridinfo", __FILE__, __LINE__);
865 0 : HEreport("\"XDim\" string not found in metadata.\n");
866 : }
867 : }
868 :
869 :
870 : /* Get ydimsize if requested */
871 : /* ------------------------- */
872 11 : if (ydimsize != NULL)
873 : {
874 11 : statmeta = EHgetmetavalue(metaptrs, "YDim", utlstr);
875 11 : if (statmeta == 0)
876 : {
877 11 : *ydimsize = atoi(utlstr);
878 : }
879 : else
880 : {
881 0 : status = -1;
882 0 : HEpush(DFE_GENAPP, "GDgridinfo", __FILE__, __LINE__);
883 0 : HEreport("\"YDim\" string not found in metadata.\n");
884 : }
885 : }
886 :
887 :
888 : /* Get upleftpt if requested */
889 : /* ------------------------- */
890 11 : if (upleftpt != NULL)
891 : {
892 4 : statmeta = EHgetmetavalue(metaptrs, "UpperLeftPointMtrs", utlstr);
893 4 : if (statmeta == 0)
894 : {
895 : /* If value is "DEFAULT" then return zeros */
896 : /* --------------------------------------- */
897 4 : if (strcmp(utlstr, "DEFAULT") == 0)
898 : {
899 0 : upleftpt[0] = 0;
900 0 : upleftpt[1] = 0;
901 : }
902 : else
903 : {
904 4 : sscanf(utlstr, "(%lf,%lf)",
905 : &upleftpt[0], &upleftpt[1]);
906 : }
907 : }
908 : else
909 : {
910 0 : status = -1;
911 0 : HEpush(DFE_GENAPP, "GDgridinfo", __FILE__, __LINE__);
912 0 : HEreport(
913 : "\"UpperLeftPointMtrs\" string not found in metadata.\n");
914 : }
915 :
916 : }
917 :
918 : /* Get lowrightpt if requested */
919 : /* --------------------------- */
920 11 : if (lowrightpt != NULL)
921 : {
922 4 : statmeta = EHgetmetavalue(metaptrs, "LowerRightMtrs", utlstr);
923 4 : if (statmeta == 0)
924 : {
925 : /* If value is "DEFAULT" then return zeros */
926 4 : if (strcmp(utlstr, "DEFAULT") == 0)
927 : {
928 0 : lowrightpt[0] = 0;
929 0 : lowrightpt[1] = 0;
930 : }
931 : else
932 : {
933 4 : sscanf(utlstr, "(%lf,%lf)",
934 : &lowrightpt[0], &lowrightpt[1]);
935 : }
936 : }
937 : else
938 : {
939 0 : status = -1;
940 0 : HEpush(DFE_GENAPP, "GDgridinfo", __FILE__, __LINE__);
941 0 : HEreport(
942 : "\"LowerRightMtrs\" string not found in metadata.\n");
943 : }
944 : }
945 :
946 11 : free(metabuf);
947 : }
948 11 : free(utlstr);
949 11 : return (status);
950 : }
951 :
952 :
953 :
954 :
955 :
956 :
957 :
958 : /*----------------------------------------------------------------------------|
959 : | BEGIN_PROLOG |
960 : | |
961 : | FUNCTION: GDprojinfo |
962 : | |
963 : | DESCRIPTION: Returns GCTP projection code, zone code, spheroid code |
964 : | and projection parameters. |
965 : | |
966 : | |
967 : | Return Value Type Units Description |
968 : | ============ ====== ========= ===================================== |
969 : | status intn return status (0) SUCCEED, (-1) FAIL |
970 : | |
971 : | INPUTS: |
972 : | gridID int32 Grid structure ID |
973 : | |
974 : | OUTPUTS: |
975 : | projcode int32 GCTP projection code |
976 : | zonecode int32 UTM zone code |
977 : | spherecode int32 GCTP spheroid code |
978 : | projparm float64 Projection parameters |
979 : | |
980 : | NOTES: |
981 : | |
982 : | |
983 : | Date Programmer Description |
984 : | ====== ============ ================================================= |
985 : | Jun 96 Joel Gales Original Programmer |
986 : | Oct 96 Joel Gales Add check for no projection code |
987 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
988 : | Jun 00 Abe Taaheri Added support for EASE grid |
989 : | |
990 : | END_PROLOG |
991 : -----------------------------------------------------------------------------*/
992 : intn
993 5 : GDprojinfo(int32 gridID, int32 * projcode, int32 * zonecode,
994 : int32 * spherecode, float64 projparm[])
995 :
996 : {
997 : intn i; /* Loop index */
998 : intn projx; /* Loop index */
999 5 : intn status = 0; /* routine return status variable */
1000 5 : intn statmeta = 0; /* EHgetmetavalue return status */
1001 :
1002 : int32 fid; /* HDF-EOS file ID */
1003 : int32 sdInterfaceID; /* HDF SDS interface ID */
1004 : int32 gdVgrpID; /* Grid root Vgroup ID */
1005 5 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1006 :
1007 :
1008 : char *metabuf; /* Pointer to structural metadata (SM) */
1009 : char *metaptrs[2];/* Pointers to begin and end of SM section */
1010 : char gridname[80]; /* Grid Name */
1011 : char *utlstr; /* Utility string */
1012 : char fmt[96]; /* Format String */
1013 :
1014 : /* Allocate space for utility string */
1015 : /* --------------------------------- */
1016 5 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1017 5 : if(utlstr == NULL)
1018 : {
1019 0 : HEpush(DFE_NOSPACE,"GDprojinfo", __FILE__, __LINE__);
1020 0 : return(-1);
1021 : }
1022 :
1023 : /* Check Grid ID */
1024 : /* ------------- */
1025 5 : status = GDchkgdid(gridID, "GDprojinfo", &fid, &sdInterfaceID, &gdVgrpID);
1026 :
1027 5 : if (status == 0)
1028 : {
1029 : /* Get grid name */
1030 : /* ------------- */
1031 5 : int gID = gridID % idOffset;
1032 5 : if (gID >= NGRID)
1033 : {
1034 0 : free(utlstr);
1035 0 : return -1;
1036 : }
1037 :
1038 5 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1039 :
1040 :
1041 : /* Get pointers to grid structure section within SM */
1042 : /* ------------------------------------------------ */
1043 5 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1044 : NULL, metaptrs);
1045 :
1046 5 : if(metabuf == NULL)
1047 : {
1048 0 : free(utlstr);
1049 0 : return(-1);
1050 : }
1051 :
1052 :
1053 : /* Get projcode if requested */
1054 : /* ------------------------- */
1055 5 : if (projcode != NULL)
1056 : {
1057 5 : *projcode = -1;
1058 :
1059 5 : statmeta = EHgetmetavalue(metaptrs, "Projection", utlstr);
1060 5 : if (statmeta == 0)
1061 : {
1062 : /* Loop through projection codes until found */
1063 : /* ----------------------------------------- */
1064 5 : for (projx = 0; Projections[projx].projcode != -1; projx++)
1065 5 : if (strcmp(utlstr, Projections[projx].projname) == 0)
1066 5 : break;
1067 5 : if (Projections[projx].projname != NULL)
1068 5 : *projcode = Projections[projx].projcode;
1069 : }
1070 : else
1071 : {
1072 0 : status = -1;
1073 0 : HEpush(DFE_GENAPP, "GDprojinfo", __FILE__, __LINE__);
1074 0 : HEreport("Projection Code not defined for \"%s\".\n",
1075 : gridname);
1076 :
1077 0 : if (projparm != NULL)
1078 : {
1079 0 : for (i = 0; i < 13; i++)
1080 : {
1081 0 : projparm[i] = -1;
1082 : }
1083 : }
1084 : }
1085 : }
1086 :
1087 :
1088 : /* Get zonecode if requested */
1089 : /* ------------------------- */
1090 5 : if (projcode && zonecode != NULL)
1091 : {
1092 5 : *zonecode = -1;
1093 :
1094 :
1095 : /* Zone code only relevant for UTM and State Code projections */
1096 : /* ---------------------------------------------------------- */
1097 5 : if (*projcode == GCTP_UTM || *projcode == GCTP_SPCS)
1098 : {
1099 0 : statmeta = EHgetmetavalue(metaptrs, "ZoneCode", utlstr);
1100 0 : if (statmeta == 0)
1101 : {
1102 0 : *zonecode = atoi(utlstr);
1103 : }
1104 : else
1105 : {
1106 0 : status = -1;
1107 0 : HEpush(DFE_GENAPP, "GDprojinfo", __FILE__, __LINE__);
1108 0 : HEreport("Zone Code not defined for \"%s\".\n",
1109 : gridname);
1110 : }
1111 : }
1112 : }
1113 :
1114 :
1115 : /* Get projection parameters if requested */
1116 : /* -------------------------------------- */
1117 5 : if (projcode && projparm != NULL)
1118 : {
1119 :
1120 : /*
1121 : * Note: No projection parameters for GEO, UTM, and State Code
1122 : * projections
1123 : */
1124 5 : if (*projcode == GCTP_GEO || *projcode == GCTP_UTM ||
1125 0 : *projcode == GCTP_SPCS)
1126 : {
1127 70 : for (i = 0; i < 13; i++)
1128 : {
1129 65 : projparm[i] = 0.0;
1130 : }
1131 :
1132 : }
1133 : else
1134 : {
1135 0 : statmeta = EHgetmetavalue(metaptrs, "ProjParams", utlstr);
1136 :
1137 0 : if (statmeta == 0)
1138 : {
1139 :
1140 : /* Build format string to read projection parameters */
1141 : /* ------------------------------------------------- */
1142 0 : strcpy(fmt, "%lf,");
1143 0 : for (i = 1; i <= 11; i++)
1144 0 : strcat(fmt, "%lf,");
1145 0 : strcat(fmt, "%lf");
1146 :
1147 :
1148 : /* Read parameters from numeric list */
1149 : /* --------------------------------- */
1150 0 : sscanf(&utlstr[1], fmt,
1151 : &projparm[0], &projparm[1],
1152 : &projparm[2], &projparm[3],
1153 : &projparm[4], &projparm[5],
1154 : &projparm[6], &projparm[7],
1155 : &projparm[8], &projparm[9],
1156 : &projparm[10], &projparm[11],
1157 : &projparm[12]);
1158 : }
1159 : else
1160 : {
1161 0 : status = -1;
1162 0 : HEpush(DFE_GENAPP, "GDprojinfo", __FILE__, __LINE__);
1163 0 : HEreport("Projection parameters not defined for \"%s\".\n",
1164 : gridname);
1165 :
1166 : }
1167 : }
1168 : }
1169 :
1170 :
1171 : /* Get spherecode if requested */
1172 : /* --------------------------- */
1173 5 : if (projcode && spherecode != NULL)
1174 : {
1175 5 : *spherecode = 0;
1176 :
1177 : /* Note: Spherecode not defined for GEO projection */
1178 : /* ----------------------------------------------- */
1179 5 : if ((*projcode != GCTP_GEO))
1180 : {
1181 0 : EHgetmetavalue(metaptrs, "SphereCode", utlstr);
1182 0 : if (statmeta == 0)
1183 : {
1184 0 : *spherecode = atoi(utlstr);
1185 : }
1186 : }
1187 : }
1188 5 : free(metabuf);
1189 :
1190 : }
1191 5 : free(utlstr);
1192 5 : return (status);
1193 : }
1194 :
1195 :
1196 :
1197 : /*----------------------------------------------------------------------------|
1198 : | BEGIN_PROLOG |
1199 : | |
1200 : | FUNCTION: GDorigininfo |
1201 : | |
1202 : | DESCRIPTION: Returns origin code |
1203 : | |
1204 : | |
1205 : | Return Value Type Units Description |
1206 : | ============ ====== ========= ===================================== |
1207 : | status intn return status (0) SUCCEED, (-1) FAIL |
1208 : | |
1209 : | INPUTS: |
1210 : | gridID int32 Grid structure ID |
1211 : | |
1212 : | |
1213 : | OUTPUTS: |
1214 : | origincode int32 grid origin code |
1215 : | |
1216 : | NOTES: |
1217 : | |
1218 : | |
1219 : | Date Programmer Description |
1220 : | ====== ============ ================================================= |
1221 : | Jun 96 Joel Gales Original Programmer |
1222 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
1223 : | |
1224 : | END_PROLOG |
1225 : -----------------------------------------------------------------------------*/
1226 : intn
1227 0 : GDorigininfo(int32 gridID, int32 * origincode)
1228 : {
1229 : intn i; /* Loop index */
1230 0 : intn status = 0; /* routine return status variable */
1231 0 : intn statmeta = 0; /* EHgetmetavalue return status */
1232 :
1233 : int32 fid; /* HDF-EOS file ID */
1234 : int32 sdInterfaceID; /* HDF SDS interface ID */
1235 : int32 gdVgrpID; /* Grid root Vgroup ID */
1236 0 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1237 :
1238 :
1239 : char *metabuf; /* Pointer to structural metadata (SM) */
1240 : char *metaptrs[2];/* Pointers to begin and end of SM section */
1241 : char gridname[80]; /* Grid Name */
1242 : char *utlstr; /* Utility string */
1243 :
1244 : /* Allocate space for utility string */
1245 : /* --------------------------------- */
1246 0 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1247 0 : if(utlstr == NULL)
1248 : {
1249 0 : HEpush(DFE_NOSPACE,"GDorigininfo", __FILE__, __LINE__);
1250 0 : return(-1);
1251 : }
1252 : /* Check Grid ID */
1253 : /* ------------- */
1254 0 : status = GDchkgdid(gridID, "GDorigininfo",
1255 : &fid, &sdInterfaceID, &gdVgrpID);
1256 :
1257 :
1258 : /* Initialize pixreg code to -1 (in case of error) */
1259 : /* ----------------------------------------------- */
1260 0 : *origincode = -1;
1261 :
1262 0 : if (status == 0)
1263 : {
1264 : /* Set default origin code */
1265 : /* ----------------------- */
1266 0 : *origincode = 0;
1267 :
1268 :
1269 : /* Get grid name */
1270 : /* ------------- */
1271 0 : int gID = gridID % idOffset;
1272 0 : if (gID >= NGRID)
1273 : {
1274 0 : free(utlstr);
1275 0 : return -1;
1276 : }
1277 :
1278 0 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1279 :
1280 :
1281 : /* Get pointers to grid structure section within SM */
1282 : /* ------------------------------------------------ */
1283 0 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1284 : NULL, metaptrs);
1285 :
1286 0 : if(metabuf == NULL)
1287 : {
1288 0 : free(utlstr);
1289 0 : return(-1);
1290 : }
1291 :
1292 :
1293 0 : statmeta = EHgetmetavalue(metaptrs, "GridOrigin", utlstr);
1294 :
1295 0 : if (statmeta == 0)
1296 : {
1297 : /*
1298 : * If "GridOrigin" string found in metadata then convert to
1299 : * numeric origin code (fixed added: Jan 97)
1300 : */
1301 0 : for (i = 0; i < (intn)(sizeof(originNames) / sizeof(originNames[0])); i++)
1302 : {
1303 0 : if (strcmp(utlstr, originNames[i]) == 0)
1304 : {
1305 0 : *origincode = i;
1306 0 : break;
1307 : }
1308 : }
1309 : }
1310 :
1311 0 : free(metabuf);
1312 : }
1313 0 : free(utlstr);
1314 0 : return (status);
1315 : }
1316 :
1317 :
1318 :
1319 :
1320 :
1321 :
1322 : /*----------------------------------------------------------------------------|
1323 : | BEGIN_PROLOG |
1324 : | |
1325 : | FUNCTION: GDpixreginfo |
1326 : | |
1327 : | DESCRIPTION: |
1328 : | |
1329 : | |
1330 : | Return Value Type Units Description |
1331 : | ============ ====== ========= ===================================== |
1332 : | status intn return status (0) SUCCEED, (-1) FAIL |
1333 : | |
1334 : | INPUTS: |
1335 : | gridID int32 Grid structure ID |
1336 : | |
1337 : | |
1338 : | OUTPUTS: |
1339 : | pixregcode int32 Pixel registration code |
1340 : | |
1341 : | |
1342 : | OUTPUTS: |
1343 : | None |
1344 : | |
1345 : | NOTES: |
1346 : | |
1347 : | |
1348 : | Date Programmer Description |
1349 : | ====== ============ ================================================= |
1350 : | Jun 96 Joel Gales Original Programmer |
1351 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
1352 : | |
1353 : | END_PROLOG |
1354 : -----------------------------------------------------------------------------*/
1355 : intn
1356 0 : GDpixreginfo(int32 gridID, int32 * pixregcode)
1357 : {
1358 : intn i; /* Loop index */
1359 0 : intn status = 0; /* routine return status variable */
1360 0 : intn statmeta = 0; /* EHgetmetavalue return status */
1361 :
1362 : int32 fid; /* HDF-EOS file ID */
1363 : int32 sdInterfaceID; /* HDF SDS interface ID */
1364 : int32 gdVgrpID; /* Grid root Vgroup ID */
1365 0 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1366 :
1367 :
1368 : char *metabuf; /* Pointer to structural metadata (SM) */
1369 : char *metaptrs[2];/* Pointers to begin and end of SM section */
1370 : char gridname[80]; /* Grid Name */
1371 : char *utlstr; /* Utility string */
1372 :
1373 : /* Allocate space for utility string */
1374 : /* --------------------------------- */
1375 0 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1376 0 : if(utlstr == NULL)
1377 : {
1378 0 : HEpush(DFE_NOSPACE,"GDpixreginfo", __FILE__, __LINE__);
1379 0 : return(-1);
1380 : }
1381 : /* Check Grid ID */
1382 0 : status = GDchkgdid(gridID, "GDpixreginfo",
1383 : &fid, &sdInterfaceID, &gdVgrpID);
1384 :
1385 : /* Initialize pixreg code to -1 (in case of error) */
1386 0 : *pixregcode = -1;
1387 :
1388 0 : if (status == 0)
1389 : {
1390 : /* Set default pixreg code */
1391 0 : *pixregcode = 0;
1392 :
1393 : /* Get grid name */
1394 0 : int gID = gridID % idOffset;
1395 0 : if (gID >= NGRID)
1396 : {
1397 0 : free(utlstr);
1398 0 : return -1;
1399 : }
1400 :
1401 0 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1402 :
1403 : /* Get pointers to grid structure section within SM */
1404 0 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1405 : NULL, metaptrs);
1406 :
1407 0 : if(metabuf == NULL)
1408 : {
1409 0 : free(utlstr);
1410 0 : return(-1);
1411 : }
1412 :
1413 :
1414 0 : statmeta = EHgetmetavalue(metaptrs, "PixelRegistration", utlstr);
1415 :
1416 0 : if (statmeta == 0)
1417 : {
1418 : /*
1419 : * If "PixelRegistration" string found in metadata then convert
1420 : * to numeric origin code (fixed added: Jan 97)
1421 : */
1422 :
1423 0 : for (i = 0; i < (intn)(sizeof(pixregNames) / sizeof(pixregNames[0])); i++)
1424 : {
1425 0 : if (strcmp(utlstr, pixregNames[i]) == 0)
1426 : {
1427 0 : *pixregcode = i;
1428 0 : break;
1429 : }
1430 : }
1431 : }
1432 0 : free(metabuf);
1433 : }
1434 0 : free(utlstr);
1435 0 : return (status);
1436 : }
1437 :
1438 :
1439 :
1440 : /*----------------------------------------------------------------------------|
1441 : | BEGIN_PROLOG |
1442 : | |
1443 : | FUNCTION: GDcompinfo |
1444 : | |
1445 : | DESCRIPTION: |
1446 : | |
1447 : | |
1448 : | Return Value Type Units Description |
1449 : | ============ ====== ========= ===================================== |
1450 : | status intn |
1451 : | |
1452 : | INPUTS: |
1453 : | gridID int32 |
1454 : | compcode int32 |
1455 : | compparm intn |
1456 : | |
1457 : | |
1458 : | OUTPUTS: |
1459 : | None |
1460 : | |
1461 : | NOTES: |
1462 : | |
1463 : | |
1464 : | Date Programmer Description |
1465 : | ====== ============ ================================================= |
1466 : | Oct 96 Joel Gales Original Programmer |
1467 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
1468 : | |
1469 : | END_PROLOG |
1470 : -----------------------------------------------------------------------------*/
1471 : intn
1472 0 : GDcompinfo(int32 gridID, const char *fieldname, int32 * compcode, intn compparm[])
1473 : {
1474 : intn i; /* Loop index */
1475 0 : intn status = 0; /* routine return status variable */
1476 0 : intn statmeta = 0; /* EHgetmetavalue return status */
1477 :
1478 : int32 fid; /* HDF-EOS file ID */
1479 : int32 sdInterfaceID; /* HDF SDS interface ID */
1480 : int32 gdVgrpID; /* Grid root Vgroup ID */
1481 0 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1482 :
1483 :
1484 : char *metabuf; /* Pointer to structural metadata (SM) */
1485 : char *metaptrs[2];/* Pointers to begin and end of SM section */
1486 : char gridname[80]; /* Grid Name */
1487 : char *utlstr;/* Utility string */
1488 :
1489 : /* Allocate space for utility string */
1490 : /* --------------------------------- */
1491 0 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1492 0 : if(utlstr == NULL)
1493 : {
1494 0 : HEpush(DFE_NOSPACE,"GDcompinfo", __FILE__, __LINE__);
1495 0 : return(-1);
1496 : }
1497 : /* Check Grid ID */
1498 0 : status = GDchkgdid(gridID, "GDcompinfo", &fid, &sdInterfaceID, &gdVgrpID);
1499 :
1500 :
1501 0 : if (status == 0)
1502 : {
1503 : /* Get grid name */
1504 0 : int gID = gridID % idOffset;
1505 0 : if (gID >= NGRID)
1506 : {
1507 0 : free(utlstr);
1508 0 : return -1;
1509 : }
1510 0 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1511 :
1512 : /* Get pointers to "DataField" section within SM */
1513 0 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1514 : "DataField", metaptrs);
1515 0 : if(metabuf == NULL)
1516 : {
1517 0 : free(utlstr);
1518 0 : return(-1);
1519 : }
1520 :
1521 :
1522 : /* Search for field */
1523 0 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "\"", fieldname, "\"\n");
1524 0 : metaptrs[0] = strstr(metaptrs[0], utlstr);
1525 :
1526 :
1527 : /* If field found and user wants compression code ... */
1528 0 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
1529 : {
1530 0 : if (compcode != NULL)
1531 : {
1532 : /* Set endptr at end of field's definition entry */
1533 0 : metaptrs[1] = strstr(metaptrs[0], "\t\t\tEND_OBJECT");
1534 :
1535 : /* Get compression type */
1536 0 : statmeta = EHgetmetavalue(metaptrs, "CompressionType", utlstr);
1537 :
1538 : /*
1539 : * Default is no compression if "CompressionType" string not
1540 : * in metadata
1541 : */
1542 0 : *compcode = HDFE_COMP_NONE;
1543 :
1544 : /* If compression code is found ... */
1545 0 : if (statmeta == 0)
1546 : {
1547 : /* Loop through compression types until match */
1548 0 : for (i = 0; i < (intn)(sizeof(HDFcomp) / sizeof(HDFcomp[0])); i++)
1549 : {
1550 0 : if (strcmp(utlstr, HDFcomp[i]) == 0)
1551 : {
1552 0 : *compcode = i;
1553 0 : break;
1554 : }
1555 : }
1556 : }
1557 : }
1558 :
1559 : /* If user wants compression parameters ... */
1560 0 : if (compparm != NULL && compcode != NULL)
1561 : {
1562 : /* Initialize to zero */
1563 0 : for (i = 0; i < 4; i++)
1564 : {
1565 0 : compparm[i] = 0;
1566 : }
1567 :
1568 : /*
1569 : * Get compression parameters if NBIT or DEFLATE compression
1570 : */
1571 0 : if (*compcode == HDFE_COMP_NBIT)
1572 : {
1573 : statmeta =
1574 0 : EHgetmetavalue(metaptrs, "CompressionParams", utlstr);
1575 0 : if (statmeta == 0)
1576 : {
1577 0 : sscanf(utlstr, "(%d,%d,%d,%d)",
1578 : &compparm[0], &compparm[1],
1579 : &compparm[2], &compparm[3]);
1580 : }
1581 : else
1582 : {
1583 0 : status = -1;
1584 0 : HEpush(DFE_GENAPP, "GDcompinfo", __FILE__, __LINE__);
1585 0 : HEreport(
1586 : "\"CompressionParams\" string not found in metadata.\n");
1587 : }
1588 : }
1589 0 : else if (*compcode == HDFE_COMP_DEFLATE)
1590 : {
1591 : statmeta =
1592 0 : EHgetmetavalue(metaptrs, "DeflateLevel", utlstr);
1593 0 : if (statmeta == 0)
1594 : {
1595 0 : sscanf(utlstr, "%d", &compparm[0]);
1596 : }
1597 : else
1598 : {
1599 0 : status = -1;
1600 0 : HEpush(DFE_GENAPP, "GDcompinfo", __FILE__, __LINE__);
1601 0 : HEreport(
1602 : "\"DeflateLevel\" string not found in metadata.\n");
1603 : }
1604 : }
1605 : }
1606 : }
1607 : else
1608 : {
1609 0 : HEpush(DFE_GENAPP, "GDcompinfo", __FILE__, __LINE__);
1610 0 : HEreport("Fieldname \"%s\" not found.\n", fieldname);
1611 : }
1612 :
1613 0 : free(metabuf);
1614 :
1615 : }
1616 0 : free(utlstr);
1617 0 : return (status);
1618 : }
1619 :
1620 :
1621 :
1622 :
1623 :
1624 :
1625 : /*----------------------------------------------------------------------------|
1626 : | BEGIN_PROLOG |
1627 : | |
1628 : | FUNCTION: GDfieldinfo |
1629 : | |
1630 : | DESCRIPTION: Retrieve information about a specific geolocation or data |
1631 : | field in the grid. |
1632 : | |
1633 : | |
1634 : | Return Value Type Units Description |
1635 : | ============ ====== ========= ===================================== |
1636 : | status intn return status (0) SUCCEED, (-1) FAIL |
1637 : | |
1638 : | INPUTS: |
1639 : | gridID int32 grid structure id |
1640 : | fieldname char name of field |
1641 : | |
1642 : | |
1643 : | OUTPUTS: |
1644 : | rank int32 rank of field (# of dims) |
1645 : | dims int32 field dimensions |
1646 : | numbertype int32 field number type |
1647 : | dimlist char field dimension list |
1648 : | |
1649 : | |
1650 : | OUTPUTS: |
1651 : | None |
1652 : | |
1653 : | NOTES: |
1654 : | |
1655 : | |
1656 : | Date Programmer Description |
1657 : | ====== ============ ================================================= |
1658 : | Jun 96 Joel Gales Original Programmer |
1659 : | Aug 96 Joel Gales Make metadata ODL compliant |
1660 : | Jan 97 Joel Gales Check for metadata error status from EHgetmetavalue |
1661 : | Feb 99 Abe Taaheri Changed memcpy to memmove to avoid overlapping |
1662 : | problem when copying strings |
1663 : | |
1664 : | END_PROLOG |
1665 : -----------------------------------------------------------------------------*/
1666 : intn
1667 107 : GDfieldinfo(int32 gridID, const char *fieldname, int32 * rank, int32 dims[],
1668 : int32 * numbertype, char *dimlist)
1669 :
1670 : {
1671 : intn i; /* Loop index */
1672 : intn status; /* routine return status variable */
1673 107 : intn statmeta = 0; /* EHgetmetavalue return status */
1674 :
1675 : int32 fid; /* HDF-EOS file ID */
1676 : int32 sdInterfaceID; /* HDF SDS interface ID */
1677 107 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1678 107 : int32 ndims = 0; /* Number of dimensions */
1679 : int32 slen[8]; /* Length of each entry in parsed string */
1680 : int32 dum; /* Dummy variable */
1681 107 : int32 xdim = 0; /* X dim size */
1682 107 : int32 ydim = 0; /* Y dim size */
1683 : int32 sdid; /* SDS id */
1684 :
1685 : char *metabuf; /* Pointer to structural metadata (SM) */
1686 : char *metaptrs[2]; /* Pointers to begin and end of SM section */
1687 : char gridname[80]; /* Grid Name */
1688 : char *utlstr; /* Utility string */
1689 : char *ptr[8]; /* String pointers for parsed string */
1690 : char dimstr[64]; /* Individual dimension entry string */
1691 :
1692 :
1693 : /* Allocate space for utility string */
1694 : /* --------------------------------- */
1695 107 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1696 107 : if(utlstr == NULL)
1697 : {
1698 0 : HEpush(DFE_NOSPACE,"GDfieldinfo", __FILE__, __LINE__);
1699 0 : return(-1);
1700 : }
1701 107 : *rank = -1;
1702 107 : *numbertype = -1;
1703 :
1704 107 : status = GDchkgdid(gridID, "GDfieldinfo", &fid, &sdInterfaceID, &dum);
1705 :
1706 107 : if (status == 0)
1707 : {
1708 107 : int gID = gridID % idOffset;
1709 107 : if (gID >= NGRID)
1710 : {
1711 0 : free(utlstr);
1712 0 : return -1;
1713 : }
1714 107 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1715 :
1716 107 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1717 : "DataField", metaptrs);
1718 107 : if(metabuf == NULL)
1719 : {
1720 0 : free(utlstr);
1721 0 : return(-1);
1722 : }
1723 :
1724 107 : if (!metaptrs[0])
1725 : {
1726 0 : free(utlstr);
1727 0 : free(metabuf);
1728 0 : return -1;
1729 : }
1730 :
1731 : /* Search for field */
1732 107 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "\"", fieldname, "\"\n");
1733 107 : metaptrs[0] = strstr(metaptrs[0], utlstr);
1734 :
1735 : /* If field found ... */
1736 107 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
1737 : {
1738 :
1739 : /* Set endptr at end of dimension definition entry */
1740 7 : metaptrs[1] = strstr(metaptrs[0], "\t\t\tEND_OBJECT");
1741 :
1742 : /* Get DataType string */
1743 7 : statmeta = EHgetmetavalue(metaptrs, "DataType", utlstr);
1744 :
1745 : /* Convert to numbertype code */
1746 7 : if (statmeta == 0)
1747 7 : *numbertype = EHnumstr(utlstr);
1748 : else
1749 : {
1750 0 : status = -1;
1751 0 : HEpush(DFE_GENAPP, "GDfieldinfo", __FILE__, __LINE__);
1752 0 : HEreport("\"DataType\" string not found in metadata.\n");
1753 : }
1754 :
1755 : /*
1756 : * Get DimList string and trim off leading and trailing parens
1757 : * "()"
1758 : */
1759 7 : statmeta = EHgetmetavalue(metaptrs, "DimList", utlstr);
1760 :
1761 7 : if (statmeta == 0)
1762 : {
1763 7 : const size_t len = strlen(utlstr);
1764 7 : if (len >= 2 && utlstr[0] == '(' && utlstr[len-1] == ')')
1765 : {
1766 4 : memmove(utlstr, utlstr + 1, len - 2);
1767 4 : utlstr[len - 2] = '\0';
1768 : }
1769 :
1770 : /* Parse trimmed DimList string and get rank */
1771 7 : ndims = EHparsestr(utlstr, ',', ptr, CPL_ARRAYSIZE(ptr), slen, CPL_ARRAYSIZE(slen));
1772 7 : if (ndims < 0)
1773 : {
1774 0 : status = -1;
1775 0 : HEpush(DFE_NOSPACE, "GDfieldinfo", __FILE__, __LINE__);
1776 : }
1777 7 : *rank = ndims;
1778 : }
1779 : else
1780 : {
1781 0 : status = -1;
1782 0 : HEpush(DFE_GENAPP, "GDfieldinfo", __FILE__, __LINE__);
1783 0 : HEreport("\"DimList\" string not found in metadata.\n");
1784 : }
1785 :
1786 :
1787 7 : if (status == 0)
1788 : {
1789 7 : status = GDgridinfo(gridID, &xdim, &ydim, NULL, NULL);
1790 :
1791 7 : dims[0] = -1;
1792 15 : for (i = 0; i < ndims; i++)
1793 : {
1794 8 : memcpy(dimstr, ptr[i] + 1, slen[i] - 2);
1795 8 : dimstr[slen[i] - 2] = 0;
1796 :
1797 8 : if (strcmp(dimstr, "XDim") == 0)
1798 : {
1799 0 : dims[i] = xdim;
1800 : }
1801 8 : else if (strcmp(dimstr, "YDim") == 0)
1802 : {
1803 4 : dims[i] = ydim;
1804 : }
1805 : else
1806 : {
1807 4 : dims[i] = GDdiminfo(gridID, dimstr);
1808 : }
1809 :
1810 :
1811 8 : if (dimlist != NULL)
1812 : {
1813 4 : if (i == 0)
1814 : {
1815 2 : dimlist[0] = 0;
1816 : }
1817 :
1818 4 : if (i > 0)
1819 : {
1820 2 : strcat(dimlist, ",");
1821 : }
1822 4 : strcat(dimlist, dimstr);
1823 : }
1824 : }
1825 :
1826 :
1827 7 : if (dims[0] == 0)
1828 : {
1829 4 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname,
1830 : &sdid, &dum, &dum, &dum, dims,
1831 : &dum);
1832 : }
1833 : }
1834 : }
1835 :
1836 107 : free(metabuf);
1837 : }
1838 :
1839 107 : if (*rank == -1)
1840 : {
1841 100 : status = -1;
1842 :
1843 100 : HEpush(DFE_GENAPP, "GDfieldinfo", __FILE__, __LINE__);
1844 100 : HEreport("Fieldname \"%s\" not found.\n", fieldname);
1845 : }
1846 107 : free(utlstr);
1847 107 : return (status);
1848 : }
1849 :
1850 :
1851 :
1852 : /*----------------------------------------------------------------------------|
1853 : | BEGIN_PROLOG |
1854 : | |
1855 : | FUNCTION: GDSDfldsrch |
1856 : | |
1857 : | DESCRIPTION: Retrieves information from SDS fields |
1858 : | |
1859 : | |
1860 : | Return Value Type Units Description |
1861 : | ============ ====== ========= ===================================== |
1862 : | status intn return status (0) SUCCEED, (-1) FAIL |
1863 : | |
1864 : | INPUTS: |
1865 : | gridID int32 grid structure ID |
1866 : | sdInterfaceID int32 SD interface ID |
1867 : | fieldname char field name |
1868 : | |
1869 : | |
1870 : | OUTPUTS: |
1871 : | sdid int32 SD element ID |
1872 : | rankSDS int32 Rank of SDS |
1873 : | rankFld int32 True rank of field (merging) |
1874 : | offset int32 Offset of field within merged field |
1875 : | dims int32 Dimensions of field |
1876 : | solo int32 Solo field flag |
1877 : | |
1878 : | NOTES: |
1879 : | |
1880 : | |
1881 : | Date Programmer Description |
1882 : | ====== ============ ================================================= |
1883 : | Jun 96 Joel Gales Original Programmer |
1884 : | Aug 96 Joel Gales Make metadata ODL compliant |
1885 : | |
1886 : | END_PROLOG |
1887 : -----------------------------------------------------------------------------*/
1888 : static intn
1889 10 : GDSDfldsrch(int32 gridID, int32 sdInterfaceID, const char *fieldname,
1890 : int32 * sdid, int32 * rankSDS, int32 * rankFld, int32 * offset,
1891 : int32 dims[], int32 * solo)
1892 : {
1893 : intn i; /* Loop index */
1894 10 : intn status = -1;/* routine return status variable */
1895 :
1896 : int32 gID; /* GridID - offset */
1897 10 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
1898 : int32 dum; /* Dummy variable */
1899 : int32 dums[128]; /* Dummy array */
1900 : int32 attrIndex; /* Attribute l_index */
1901 :
1902 : char name[2048]; /* Merged-Field Names */
1903 : char gridname[80]; /* Grid Name */
1904 : char *utlstr;/* Utility string */
1905 : char *metabuf; /* Pointer to structural metadata (SM) */
1906 : char *metaptrs[2];/* Pointers to begin and end of SM section */
1907 : #ifdef broken_logic
1908 : char *oldmetaptr; /* Pointer within SM section */
1909 : char *metaptr; /* Pointer within SM section */
1910 : #endif
1911 :
1912 : /* Allocate space for utility string */
1913 : /* --------------------------------- */
1914 10 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
1915 10 : if(utlstr == NULL)
1916 : {
1917 0 : HEpush(DFE_NOSPACE,"GDSDfldsrch", __FILE__, __LINE__);
1918 0 : return(-1);
1919 : }
1920 : /* Set solo flag to 0 (no) */
1921 : /* ----------------------- */
1922 10 : *solo = 0;
1923 :
1924 :
1925 : /* Compute "reduced" grid ID */
1926 : /* ------------------------- */
1927 10 : gID = gridID % idOffset;
1928 10 : if (gID >= NGRID)
1929 : {
1930 0 : free(utlstr);
1931 0 : return -1;
1932 : }
1933 :
1934 : /* Loop through all SDSs in grid */
1935 : /* ----------------------------- */
1936 15 : for (i = 0; i < GDXGrid[gID].nSDS; i++)
1937 : {
1938 : /* If active SDS ... */
1939 : /* ----------------- */
1940 5 : if (GDXGrid[gID].sdsID[i] != 0)
1941 : {
1942 : /* Get SDS ID, name, rankSDS, and dimensions */
1943 : /* ----------------------------------------- */
1944 5 : *sdid = GDXGrid[gID].sdsID[i];
1945 5 : SDgetinfo(*sdid, name, rankSDS, dims, &dum, &dum);
1946 5 : *rankFld = *rankSDS;
1947 :
1948 :
1949 : /* If merged field ... */
1950 : /* ------------------- */
1951 5 : if (strstr(name, "MRGFLD_") == &name[0])
1952 : {
1953 : /* Get grid name */
1954 : /* ------------- */
1955 5 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
1956 :
1957 :
1958 : /* Get pointers to "MergedFields" section within SM */
1959 : /* ------------------------------------------------ */
1960 5 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
1961 : "MergedFields", metaptrs);
1962 5 : if(metabuf == NULL)
1963 : {
1964 0 : free(utlstr);
1965 0 : return(-1);
1966 : }
1967 :
1968 : #ifdef broken_logic
1969 : /* Initialize metaptr to beg. of section */
1970 : /* ------------------------------------- */
1971 : metaptr = metaptrs[0];
1972 :
1973 :
1974 : /* Store metaptr in order to recover */
1975 : /* --------------------------------- */
1976 : oldmetaptr = metaptr;
1977 :
1978 :
1979 : /* Search for Merged field name */
1980 : /* ---------------------------- */
1981 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "MergedFieldName=\"",
1982 : name, "\"\n");
1983 : metaptr = strstr(metaptr, utlstr);
1984 :
1985 :
1986 : /* If not found check for old metadata */
1987 : /* ----------------------------------- */
1988 : if (metaptr == NULL)
1989 : {
1990 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "OBJECT=\"", name, "\"\n");
1991 : metaptr = strstr(oldmetaptr, utlstr);
1992 : }
1993 : #endif
1994 :
1995 : /* Get field list and strip off leading and trailing quotes */
1996 : /* -------------------------------------------------------- */
1997 5 : if (EHgetmetavalue(metaptrs, "FieldList", name) == 0)
1998 : {
1999 5 : const size_t len = strlen(name);
2000 5 : if (len >= 2 && name[0] == '"' && name[len-1] == '"')
2001 : {
2002 0 : memmove(name, name + 1, strlen(name) - 2);
2003 0 : name[strlen(name) - 2] = 0;
2004 : }
2005 : }
2006 : else
2007 : {
2008 0 : name[0] = '\0';
2009 : }
2010 :
2011 : /* Search for desired field within merged field list */
2012 : /* ------------------------------------------------- */
2013 5 : snprintf(utlstr, UTLSTR_MAX_SIZE, "%s%s%s", "\"", fieldname, "\"");
2014 5 : dum = EHstrwithin(utlstr, name, ',');
2015 :
2016 5 : free(metabuf);
2017 : }
2018 : else
2019 : {
2020 : /* If solo (unmerged) check if SDS name matches fieldname */
2021 : /* ------------------------------------------------------ */
2022 0 : dum = EHstrwithin(fieldname, name, ',');
2023 0 : if (dum != -1)
2024 : {
2025 0 : *solo = 1;
2026 0 : *offset = 0;
2027 : }
2028 : }
2029 :
2030 :
2031 :
2032 : /* If field found ... */
2033 : /* ------------------ */
2034 5 : if (dum != -1)
2035 : {
2036 0 : status = 0;
2037 :
2038 : /* If merged field ... */
2039 : /* ------------------- */
2040 0 : if (*solo == 0)
2041 : {
2042 : /* Get "Field Offsets" SDS attribute l_index */
2043 : /* --------------------------------------- */
2044 0 : attrIndex = SDfindattr(*sdid, "Field Offsets");
2045 :
2046 : /*
2047 : * If attribute exists then get offset of desired field
2048 : * within merged field
2049 : */
2050 0 : if (attrIndex != -1)
2051 : {
2052 0 : SDreadattr(*sdid, attrIndex, (VOIDP) dums);
2053 0 : *offset = dums[dum];
2054 : }
2055 :
2056 :
2057 : /* Get "Field Dims" SDS attribute l_index */
2058 : /* ------------------------------------ */
2059 0 : attrIndex = SDfindattr(*sdid, "Field Dims");
2060 :
2061 : /*
2062 : * If attribute exists then get 0th dimension of desired
2063 : * field within merged field
2064 : */
2065 0 : if (attrIndex != -1)
2066 : {
2067 0 : SDreadattr(*sdid, attrIndex, (VOIDP) dums);
2068 0 : dims[0] = dums[dum];
2069 :
2070 : /* If this dimension = 1 then field is really 2 dim */
2071 : /* ------------------------------------------------ */
2072 0 : if (dums[dum] == 1)
2073 : {
2074 0 : *rankFld = 2;
2075 : }
2076 : }
2077 : }
2078 :
2079 :
2080 : /* Break out of SDS loop */
2081 : /* --------------------- */
2082 0 : break;
2083 : } /* End of found field section */
2084 : }
2085 : else
2086 : {
2087 : /* First non-active SDS signifies no more, break out of SDS loop */
2088 : /* ------------------------------------------------------------- */
2089 0 : break;
2090 : }
2091 : }
2092 10 : free(utlstr);
2093 10 : return (status);
2094 : }
2095 :
2096 :
2097 :
2098 :
2099 : /*----------------------------------------------------------------------------|
2100 : | BEGIN_PROLOG |
2101 : | |
2102 : | FUNCTION: GDwrrdfield |
2103 : | |
2104 : | DESCRIPTION: Writes/Reads fields |
2105 : | |
2106 : | |
2107 : | Return Value Type Units Description |
2108 : | ============ ====== ========= ===================================== |
2109 : | status intn return status (0) SUCCEED, (-1) FAIL |
2110 : | |
2111 : | INPUTS: |
2112 : | gridID int32 grid structure ID |
2113 : | fieldname char fieldname |
2114 : | code char Write/Read code (w/r) |
2115 : | start int32 start array |
2116 : | stride int32 stride array |
2117 : | edge int32 edge array |
2118 : | datbuf void data buffer for read |
2119 : | |
2120 : | |
2121 : | OUTPUTS: |
2122 : | datbuf void data buffer for write |
2123 : | |
2124 : | |
2125 : | NOTES: |
2126 : | |
2127 : | |
2128 : | Date Programmer Description |
2129 : | ====== ============ ================================================= |
2130 : | Jun 96 Joel Gales Original Programmer |
2131 : | Feb 97 Joel Gales Stride = 1 HDF compression workaround |
2132 : | |
2133 : | END_PROLOG |
2134 : -----------------------------------------------------------------------------*/
2135 : static intn
2136 0 : GDwrrdfield(int32 gridID, const char *fieldname, const char *code,
2137 : int32 start[], int32 stride[], int32 edge[], VOIDP datbuf)
2138 :
2139 : {
2140 : intn i; /* Loop index */
2141 0 : intn status = 0; /* routine return status variable */
2142 :
2143 : int32 fid; /* HDF-EOS file ID */
2144 : int32 sdInterfaceID; /* HDF SDS interface ID */
2145 : int32 sdid; /* SDS ID */
2146 : int32 dum; /* Dummy variable */
2147 : int32 rankSDS; /* Rank of SDS */
2148 : int32 rankFld; /* Rank of field */
2149 :
2150 0 : int32 offset[8] = {0}; /* I/O offset (start) */
2151 : int32 incr[8]; /* I/O increment (stride) */
2152 : int32 count[8]; /* I/O count (edge) */
2153 : int32 dims[8]; /* Field/SDS dimensions */
2154 0 : int32 mrgOffset = 0; /* Merged field offset */
2155 : int32 strideOne; /* Strides = 1 flag */
2156 :
2157 0 : for (i = 0; i < 8; ++i)
2158 0 : incr[i] = 1;
2159 :
2160 : /* Check for valid grid ID */
2161 : /* ----------------------- */
2162 0 : status = GDchkgdid(gridID, "GDwrrdfield", &fid, &sdInterfaceID, &dum);
2163 0 : if (status < 0)
2164 0 : return -1;
2165 :
2166 : /* Check that field exists */
2167 : /* ----------------------- */
2168 0 : status = GDfieldinfo(gridID, fieldname, &rankSDS, dims, &dum, NULL);
2169 :
2170 :
2171 0 : if (status != 0)
2172 : {
2173 0 : HEpush(DFE_GENAPP, "GDwrrdfield", __FILE__, __LINE__);
2174 0 : HEreport("Fieldname \"%s\" does not exist.\n", fieldname);
2175 0 : status = -1;
2176 :
2177 : }
2178 :
2179 :
2180 0 : if (status == 0)
2181 : {
2182 0 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname, &sdid,
2183 : &rankSDS, &rankFld, &mrgOffset, dims, &dum);
2184 0 : if (status < 0)
2185 0 : return -1;
2186 :
2187 :
2188 : /* Set I/O offset Section */
2189 : /* ---------------------- */
2190 :
2191 : /*
2192 : * If start == NULL (default) set I/O offset of 0th field to
2193 : * offset within merged field (if any) and the rest to 0
2194 : */
2195 0 : if (start == NULL)
2196 : {
2197 0 : for (i = 0; i < rankSDS; i++)
2198 : {
2199 0 : offset[i] = 0;
2200 : }
2201 0 : offset[0] = mrgOffset;
2202 : }
2203 : else
2204 : {
2205 : /*
2206 : * ... otherwise set I/O offset to user values, adjusting the
2207 : * 0th field with the merged field offset (if any)
2208 : */
2209 0 : if (rankFld == rankSDS)
2210 : {
2211 0 : for (i = 0; i < rankSDS; i++)
2212 : {
2213 0 : offset[i] = start[i];
2214 : }
2215 0 : offset[0] += mrgOffset;
2216 : }
2217 : else
2218 : {
2219 : /*
2220 : * If field really 2-dim merged in 3-dim field then set
2221 : * 0th field offset to merge offset and then next two to
2222 : * the user values
2223 : */
2224 0 : for (i = 0; i < rankFld; i++)
2225 : {
2226 0 : offset[i + 1] = start[i];
2227 : }
2228 0 : offset[0] = mrgOffset;
2229 : }
2230 : }
2231 :
2232 :
2233 :
2234 : /* Set I/O stride Section */
2235 : /* ---------------------- */
2236 :
2237 : /*
2238 : * If stride == NULL (default) set I/O stride to 1
2239 : */
2240 0 : if (stride == NULL)
2241 : {
2242 0 : for (i = 0; i < rankSDS; i++)
2243 : {
2244 0 : incr[i] = 1;
2245 : }
2246 : }
2247 : else
2248 : {
2249 : /*
2250 : * ... otherwise set I/O stride to user values
2251 : */
2252 0 : if (rankFld == rankSDS)
2253 : {
2254 0 : for (i = 0; i < rankSDS; i++)
2255 : {
2256 0 : incr[i] = stride[i];
2257 : }
2258 : }
2259 : else
2260 : {
2261 : /*
2262 : * If field really 2-dim merged in 3-dim field then set
2263 : * 0th field stride to 1 and then next two to the user
2264 : * values.
2265 : */
2266 0 : for (i = 0; i < rankFld; i++)
2267 : {
2268 0 : incr[i + 1] = stride[i];
2269 : }
2270 0 : incr[0] = 1;
2271 : }
2272 : }
2273 :
2274 :
2275 :
2276 : /* Set I/O count Section */
2277 : /* --------------------- */
2278 :
2279 : /*
2280 : * If edge == NULL (default) set I/O count to number of remaining
2281 : * entries (dims - start) / increment. Note that 0th field
2282 : * offset corrected for merged field offset (if any).
2283 : */
2284 0 : if (edge == NULL)
2285 : {
2286 0 : for (i = 1; i < rankSDS; i++)
2287 : {
2288 0 : count[i] = (dims[i] - offset[i]) / incr[i];
2289 : }
2290 0 : count[0] = (dims[0] - (offset[0] - mrgOffset)) / incr[0];
2291 : }
2292 : else
2293 : {
2294 : /*
2295 : * ... otherwise set I/O count to user values
2296 : */
2297 0 : if (rankFld == rankSDS)
2298 : {
2299 0 : for (i = 0; i < rankSDS; i++)
2300 : {
2301 0 : count[i] = edge[i];
2302 : }
2303 : }
2304 : else
2305 : {
2306 : /*
2307 : * If field really 2-dim merged in 3-dim field then set
2308 : * 0th field count to 1 and then next two to the user
2309 : * values.
2310 : */
2311 0 : for (i = 0; i < rankFld; i++)
2312 : {
2313 0 : count[i + 1] = edge[i];
2314 : }
2315 0 : count[0] = 1;
2316 : }
2317 : }
2318 :
2319 :
2320 : /* Perform I/O with relevant HDF I/O routine */
2321 : /* ----------------------------------------- */
2322 0 : if (strcmp(code, "w") == 0)
2323 : {
2324 : /* Set strideOne to true (1) */
2325 : /* ------------------------- */
2326 0 : strideOne = 1;
2327 :
2328 :
2329 : /* If incr[i] != 1 set strideOne to false (0) */
2330 : /* ------------------------------------------ */
2331 0 : for (i = 0; i < rankSDS; i++)
2332 : {
2333 0 : if (incr[i] != 1)
2334 : {
2335 0 : strideOne = 0;
2336 0 : break;
2337 : }
2338 : }
2339 :
2340 :
2341 : /*
2342 : * If strideOne is true use NULL parameter for stride. This
2343 : * is a work-around to HDF compression problem
2344 : */
2345 0 : if (strideOne == 1)
2346 : {
2347 0 : status = SDwritedata(sdid, offset, NULL, count,
2348 : (VOIDP) datbuf);
2349 : }
2350 : else
2351 : {
2352 0 : status = SDwritedata(sdid, offset, incr, count,
2353 : (VOIDP) datbuf);
2354 : }
2355 : }
2356 : else
2357 : {
2358 0 : status = SDreaddata(sdid, offset, incr, count,
2359 : (VOIDP) datbuf);
2360 : }
2361 : }
2362 :
2363 0 : return (status);
2364 : }
2365 :
2366 :
2367 : /*----------------------------------------------------------------------------|
2368 : | BEGIN_PROLOG |
2369 : | |
2370 : | FUNCTION: GDreadfield |
2371 : | |
2372 : | DESCRIPTION: Reads data from a grid field. |
2373 : | |
2374 : | |
2375 : | Return Value Type Units Description |
2376 : | ============ ====== ========= ===================================== |
2377 : | status intn return status (0) SUCCEED, (-1) FAIL |
2378 : | |
2379 : | INPUTS: |
2380 : | gridID int32 grid structure ID |
2381 : | fieldname char fieldname |
2382 : | start int32 start array |
2383 : | stride int32 stride array |
2384 : | edge int32 edge array |
2385 : | buffer void data buffer for read |
2386 : | |
2387 : | |
2388 : | OUTPUTS: |
2389 : | None |
2390 : | |
2391 : | NOTES: |
2392 : | |
2393 : | |
2394 : | Date Programmer Description |
2395 : | ====== ============ ================================================= |
2396 : | Jun 96 Joel Gales Original Programmer |
2397 : | |
2398 : | END_PROLOG |
2399 : -----------------------------------------------------------------------------*/
2400 : intn
2401 0 : GDreadfield(int32 gridID, const char *fieldname,
2402 : int32 start[], int32 stride[], int32 edge[], VOIDP buffer)
2403 :
2404 : {
2405 0 : intn status = 0; /* routine return status variable */
2406 :
2407 0 : status = GDwrrdfield(gridID, fieldname, "r", start, stride, edge,
2408 : buffer);
2409 0 : return (status);
2410 : }
2411 :
2412 :
2413 :
2414 :
2415 : /*----------------------------------------------------------------------------|
2416 : | BEGIN_PROLOG |
2417 : | |
2418 : | FUNCTION: GDwrrdattr |
2419 : | |
2420 : | DESCRIPTION: |
2421 : | |
2422 : | |
2423 : | Return Value Type Units Description |
2424 : | ============ ====== ========= ===================================== |
2425 : | status intn return status (0) SUCCEED, (-1) FAIL |
2426 : | |
2427 : | INPUTS: |
2428 : | gridID int32 grid structure ID |
2429 : | attrname char attribute name |
2430 : | numbertype int32 attribute HDF numbertype |
2431 : | count int32 Number of attribute elements |
2432 : | wrcode char Read/Write Code "w/r" |
2433 : | datbuf void I/O buffer |
2434 : | |
2435 : | OUTPUTS: |
2436 : | datbuf |
2437 : | |
2438 : | NOTES: |
2439 : | |
2440 : | |
2441 : | Date Programmer Description |
2442 : | ====== ============ ================================================= |
2443 : | Jun 96 Joel Gales Original Programmer |
2444 : | Oct 96 Joel Gales Get Attribute Vgroup ID from external array |
2445 : | |
2446 : | END_PROLOG |
2447 : -----------------------------------------------------------------------------*/
2448 : static intn
2449 1 : GDwrrdattr(int32 gridID, const char *attrname, int32 numbertype, int32 count,
2450 : const char *wrcode, VOIDP datbuf)
2451 :
2452 : {
2453 : intn status; /* routine return status variable */
2454 :
2455 : int32 fid; /* HDF-EOS file ID */
2456 : int32 attrVgrpID; /* Grid attribute ID */
2457 : int32 dum; /* dummy variable */
2458 1 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
2459 :
2460 :
2461 : /* Check Grid id */
2462 1 : status = GDchkgdid(gridID, "GDwrrdattr", &fid, &dum, &dum);
2463 :
2464 1 : if (status == 0)
2465 : {
2466 : /* Perform Attribute I/O */
2467 : /* --------------------- */
2468 1 : int gID = gridID % idOffset;
2469 1 : if (gID >= NGRID)
2470 : {
2471 0 : return -1;
2472 : }
2473 1 : attrVgrpID = GDXGrid[gID].VIDTable[1];
2474 1 : status = EHattr(fid, attrVgrpID, attrname, numbertype, count,
2475 : wrcode, datbuf);
2476 : }
2477 1 : return (status);
2478 : }
2479 :
2480 : /*----------------------------------------------------------------------------|
2481 : | BEGIN_PROLOG |
2482 : | |
2483 : | FUNCTION: GDreadattr |
2484 : | |
2485 : | DESCRIPTION: Reads attribute from a grid. |
2486 : | |
2487 : | |
2488 : | Return Value Type Units Description |
2489 : | ============ ====== ========= ===================================== |
2490 : | status intn return status (0) SUCCEED, (-1) FAIL |
2491 : | |
2492 : | INPUTS: |
2493 : | gridID int32 grid structure ID |
2494 : | attrname char attribute name |
2495 : | |
2496 : | OUTPUTS: |
2497 : | datbuf void I/O buffer |
2498 : | |
2499 : | NOTES: |
2500 : | |
2501 : | |
2502 : | Date Programmer Description |
2503 : | ====== ============ ================================================= |
2504 : | Jun 96 Joel Gales Original Programmer |
2505 : | |
2506 : | END_PROLOG |
2507 : -----------------------------------------------------------------------------*/
2508 : intn
2509 1 : GDreadattr(int32 gridID, const char *attrname, VOIDP datbuf)
2510 : {
2511 1 : intn status = 0; /* routine return status variable */
2512 1 : int32 dum = 0; /* dummy variable */
2513 :
2514 : /* Call GDwrrdattr routine to read attribute */
2515 : /* ----------------------------------------- */
2516 1 : status = GDwrrdattr(gridID, attrname, dum, dum, "r", datbuf);
2517 :
2518 1 : return (status);
2519 : }
2520 :
2521 :
2522 :
2523 :
2524 :
2525 : /*----------------------------------------------------------------------------|
2526 : | BEGIN_PROLOG |
2527 : | |
2528 : | FUNCTION: GDattrinfo |
2529 : | |
2530 : | DESCRIPTION: |
2531 : | |
2532 : | |
2533 : | Return Value Type Units Description |
2534 : | ============ ====== ========= ===================================== |
2535 : | status intn return status (0) SUCCEED, (-1) FAIL |
2536 : | |
2537 : | INPUTS: |
2538 : | gridID int32 grid structure ID |
2539 : | attrname char attribute name |
2540 : | |
2541 : | OUTPUTS: |
2542 : | numbertype int32 attribute HDF numbertype |
2543 : | count int32 Number of attribute elements |
2544 : | |
2545 : | |
2546 : | OUTPUTS: |
2547 : | None |
2548 : | |
2549 : | NOTES: |
2550 : | |
2551 : | |
2552 : | Date Programmer Description |
2553 : | ====== ============ ================================================= |
2554 : | Jun 96 Joel Gales Original Programmer |
2555 : | Oct 96 Joel Gales Get Attribute Vgroup ID from external array |
2556 : | |
2557 : | END_PROLOG |
2558 : -----------------------------------------------------------------------------*/
2559 : intn
2560 0 : GDattrinfo(int32 gridID, const char *attrname, int32 * numbertype, int32 * count)
2561 : {
2562 0 : intn status = 0; /* routine return status variable */
2563 :
2564 0 : int32 fid = 0; /* HDF-EOS file ID */
2565 : int32 attrVgrpID; /* Grid attribute ID */
2566 : int32 dum; /* dummy variable */
2567 0 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
2568 :
2569 0 : status = GDchkgdid(gridID, "GDattrinfo", &fid, &dum, &dum);
2570 0 : if (status < 0)
2571 0 : return -1;
2572 :
2573 0 : int gID = gridID % idOffset;
2574 0 : if (gID >= NGRID)
2575 : {
2576 0 : return -1;
2577 : }
2578 0 : attrVgrpID = GDXGrid[gID].VIDTable[1];
2579 :
2580 0 : status = EHattrinfo(fid, attrVgrpID, attrname, numbertype,
2581 : count);
2582 :
2583 0 : return (status);
2584 : }
2585 :
2586 :
2587 :
2588 :
2589 :
2590 :
2591 : /*----------------------------------------------------------------------------|
2592 : | BEGIN_PROLOG |
2593 : | |
2594 : | FUNCTION: GDinqattrs |
2595 : | |
2596 : | DESCRIPTION: |
2597 : | |
2598 : | |
2599 : | Return Value Type Units Description |
2600 : | ============ ====== ========= ===================================== |
2601 : | nattr int32 Number of attributes in swath struct |
2602 : | |
2603 : | INPUTS: |
2604 : | grid ID int32 grid structure ID |
2605 : | |
2606 : | OUTPUTS: |
2607 : | attrnames char Attribute names in swath struct |
2608 : | (Comma-separated list) |
2609 : | strbufsize int32 Attributes name list string length |
2610 : | |
2611 : | OUTPUTS: |
2612 : | None |
2613 : | |
2614 : | NOTES: |
2615 : | |
2616 : | |
2617 : | Date Programmer Description |
2618 : | ====== ============ ================================================= |
2619 : | Jun 96 Joel Gales Original Programmer |
2620 : | Oct 96 Joel Gales Initialize nattr |
2621 : | Oct 96 Joel Gales Get Attribute Vgroup ID from external array |
2622 : | |
2623 : | END_PROLOG |
2624 : -----------------------------------------------------------------------------*/
2625 : int32
2626 4 : GDinqattrs(int32 gridID, char *attrnames, int32 * strbufsize)
2627 : {
2628 : intn status; /* routine return status variable */
2629 :
2630 : int32 fid; /* HDF-EOS file ID */
2631 : int32 attrVgrpID; /* Grid attribute ID */
2632 : int32 dum; /* dummy variable */
2633 4 : int32 nattr = 0; /* Number of attributes */
2634 4 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
2635 :
2636 :
2637 : /* Check Grid id */
2638 4 : status = GDchkgdid(gridID, "GDinqattrs", &fid, &dum, &dum);
2639 :
2640 4 : if (status == 0)
2641 : {
2642 4 : int gID = gridID % idOffset;
2643 4 : if (gID >= NGRID)
2644 : {
2645 0 : return -1;
2646 : }
2647 4 : attrVgrpID = GDXGrid[gID].VIDTable[1];
2648 4 : nattr = EHattrcat(fid, attrVgrpID, attrnames, strbufsize);
2649 : }
2650 :
2651 4 : return (nattr);
2652 : }
2653 :
2654 :
2655 :
2656 :
2657 :
2658 :
2659 : #define REMQUOTE(x) do { \
2660 : char* l_x = x; \
2661 : const size_t l_x_len = strlen(l_x); \
2662 : if (l_x_len >= 2 && l_x[0] == '"' && l_x[l_x_len - 1] == '"') {\
2663 : memmove(l_x, l_x + 1, l_x_len - 2); \
2664 : l_x[l_x_len - 2] = 0; \
2665 : } \
2666 : } while(0)
2667 :
2668 :
2669 : /*----------------------------------------------------------------------------|
2670 : | BEGIN_PROLOG |
2671 : | |
2672 : | FUNCTION: GDinqdims |
2673 : | |
2674 : | DESCRIPTION: Retrieve information about all dimensions defined in a grid. |
2675 : | |
2676 : | |
2677 : | Return Value Type Units Description |
2678 : | ============ ====== ========= ===================================== |
2679 : | nDim int32 Number of defined dimensions |
2680 : | |
2681 : | INPUTS: |
2682 : | gridID int32 grid structure ID |
2683 : | |
2684 : | OUTPUTS: |
2685 : | dimnames char Dimension names (comma-separated) |
2686 : | dims int32 Dimension values |
2687 : | |
2688 : | |
2689 : | OUTPUTS: |
2690 : | None |
2691 : | |
2692 : | NOTES: |
2693 : | |
2694 : | |
2695 : | Date Programmer Description |
2696 : | ====== ============ ================================================= |
2697 : | Jun 96 Joel Gales Original Programmer |
2698 : | Aug 96 Joel Gales Make metadata ODL compliant |
2699 : | Feb 97 Joel Gales Set nDim to -1 if status = -1 |
2700 : | |
2701 : | END_PROLOG |
2702 : -----------------------------------------------------------------------------*/
2703 : int32
2704 0 : GDinqdims(int32 gridID, char *dimnames, int32 dims[])
2705 : {
2706 : intn status; /* routine return status variable */
2707 :
2708 : int32 fid; /* HDF-EOS file ID */
2709 : int32 sdInterfaceID; /* HDF SDS interface ID */
2710 : int32 gdVgrpID; /* Grid root Vgroup ID */
2711 : int32 size; /* Dimension size */
2712 0 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
2713 0 : int32 nDim = 0; /* Number of dimensions */
2714 :
2715 : char *metabuf; /* Pointer to structural metadata (SM) */
2716 : char *metaptrs[2];/* Pointers to begin and end of SM section */
2717 : char gridname[80]; /* Grid Name */
2718 : char *utlstr;/* Utility string */
2719 :
2720 : /* Allocate space for utility string */
2721 : /* --------------------------------- */
2722 0 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
2723 0 : if(utlstr == NULL)
2724 : {
2725 0 : HEpush(DFE_NOSPACE,"GDinqdims", __FILE__, __LINE__);
2726 0 : return(-1);
2727 : }
2728 : /* Check for valid grid id */
2729 : /* ----------------------- */
2730 0 : status = GDchkgdid(gridID, "GDinqdims", &fid, &sdInterfaceID, &gdVgrpID);
2731 :
2732 0 : if (status == 0)
2733 : {
2734 : /* If dimension names or sizes are requested */
2735 : /* ----------------------------------------- */
2736 0 : if (dimnames != NULL || dims != NULL)
2737 : {
2738 : /* Get grid name */
2739 : /* ------------- */
2740 0 : int gID = gridID % idOffset;
2741 0 : if (gID >= NGRID)
2742 : {
2743 0 : free(utlstr);
2744 0 : return -1;
2745 : }
2746 0 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
2747 :
2748 :
2749 : /* Get pointers to "Dimension" section within SM */
2750 : /* --------------------------------------------- */
2751 0 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
2752 : "Dimension", metaptrs);
2753 0 : if(metabuf == NULL)
2754 : {
2755 0 : free(utlstr);
2756 0 : return(-1);
2757 : }
2758 :
2759 :
2760 : /* If dimension names are requested then "clear" name buffer */
2761 : /* --------------------------------------------------------- */
2762 0 : if (dimnames != NULL)
2763 : {
2764 0 : dimnames[0] = 0;
2765 : }
2766 :
2767 0 : while (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
2768 : {
2769 0 : strcpy(utlstr, "\t\tOBJECT=");
2770 0 : metaptrs[0] = strstr(metaptrs[0], utlstr);
2771 0 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
2772 : {
2773 : /* Get Dimension Name */
2774 : /* ------------------ */
2775 0 : if (dimnames != NULL)
2776 : {
2777 : /* Check 1st for old meta data then new */
2778 : /* ------------------------------------ */
2779 0 : EHgetmetavalue(metaptrs, "OBJECT", utlstr);
2780 0 : if (utlstr[0] != '"')
2781 : {
2782 0 : metaptrs[0] =
2783 0 : strstr(metaptrs[0], "\t\t\t\tDimensionName=");
2784 0 : EHgetmetavalue(metaptrs, "DimensionName", utlstr);
2785 : }
2786 :
2787 : /* Strip off double quotes */
2788 : /* ----------------------- */
2789 0 : memmove(utlstr, utlstr + 1, strlen(utlstr) - 2);
2790 0 : utlstr[strlen(utlstr) - 2] = 0;
2791 :
2792 0 : if (nDim > 0)
2793 : {
2794 0 : strcat(dimnames, ",");
2795 : }
2796 0 : strcat(dimnames, utlstr);
2797 : }
2798 :
2799 : /* Get Dimension Size */
2800 : /* ------------------ */
2801 0 : if (dims != NULL)
2802 : {
2803 0 : EHgetmetavalue(metaptrs, "Size", utlstr);
2804 0 : size = atoi(utlstr);
2805 0 : dims[nDim] = size;
2806 : }
2807 0 : nDim++;
2808 : }
2809 : }
2810 0 : free(metabuf);
2811 :
2812 : }
2813 : }
2814 :
2815 :
2816 : /* Set nDim to -1 if error status exists */
2817 : /* ------------------------------------- */
2818 0 : if (status == -1)
2819 : {
2820 0 : nDim = -1;
2821 : }
2822 0 : free(utlstr);
2823 0 : return (nDim);
2824 : }
2825 :
2826 :
2827 :
2828 :
2829 :
2830 :
2831 : /*----------------------------------------------------------------------------|
2832 : | BEGIN_PROLOG |
2833 : | |
2834 : | FUNCTION: GDinqfields |
2835 : | |
2836 : | DESCRIPTION: Retrieve information about all data fields defined in a grid. |
2837 : | |
2838 : | |
2839 : | Return Value Type Units Description |
2840 : | ============ ====== ========= ===================================== |
2841 : | nFld int32 Number of fields in swath |
2842 : | |
2843 : | INPUTS: |
2844 : | gridID int32 grid structure ID |
2845 : | |
2846 : | |
2847 : | OUTPUTS: |
2848 : | fieldlist char Field names (comma-separated) |
2849 : | rank int32 Array of ranks |
2850 : | numbertype int32 Array of HDF number types |
2851 : | |
2852 : | NOTES: |
2853 : | |
2854 : | |
2855 : | Date Programmer Description |
2856 : | ====== ============ ================================================= |
2857 : | Jun 96 Joel Gales Original Programmer |
2858 : | Aug 96 Joel Gales Make metadata ODL compliant |
2859 : | Feb 97 Joel Gales Set nFld to -1 if status = -1 |
2860 : | |
2861 : | END_PROLOG |
2862 : -----------------------------------------------------------------------------*/
2863 : int32
2864 6 : GDinqfields(int32 gridID, char *fieldlist, int32 rank[],
2865 : int32 numbertype[])
2866 : {
2867 : intn status; /* routine return status variable */
2868 :
2869 : int32 fid; /* HDF-EOS file ID */
2870 : int32 sdInterfaceID; /* HDF SDS interface ID */
2871 : int32 gdVgrpID; /* Grid root Vgroup ID */
2872 6 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
2873 6 : int32 nFld = 0; /* Number of mappings */
2874 : int32 slen[8]; /* String length array */
2875 :
2876 : char *metabuf; /* Pointer to structural metadata (SM) */
2877 : char *metaptrs[2];/* Pointers to begin and end of SM section */
2878 : char gridname[80]; /* Grid Name */
2879 : char *utlstr;/* Utility string */
2880 : char *ptr[8]; /* String pointer array */
2881 :
2882 : /* Allocate space for utility string */
2883 : /* --------------------------------- */
2884 6 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
2885 6 : if(utlstr == NULL)
2886 : {
2887 0 : HEpush(DFE_NOSPACE,"GDinqfields", __FILE__, __LINE__);
2888 0 : return(-1);
2889 : }
2890 : /* Check for valid grid id */
2891 : /* ----------------------- */
2892 6 : status = GDchkgdid(gridID, "GDinqfields", &fid, &sdInterfaceID, &gdVgrpID);
2893 6 : if (status == 0)
2894 : {
2895 :
2896 : /* If field names, ranks, or number types desired ... */
2897 : /* --------------------------------------------------- */
2898 6 : if (fieldlist != NULL || rank != NULL || numbertype != NULL)
2899 : {
2900 : /* Get grid name */
2901 : /* ------------- */
2902 6 : int gID = gridID % idOffset;
2903 6 : if (gID >= NGRID)
2904 : {
2905 0 : free(utlstr);
2906 0 : return -1;
2907 : }
2908 6 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
2909 :
2910 :
2911 : /* Get pointers to "DataField" section within SM */
2912 : /* --------------------------------------------- */
2913 6 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
2914 : "DataField", metaptrs);
2915 6 : if(metabuf == NULL)
2916 : {
2917 0 : free(utlstr);
2918 0 : return(-1);
2919 : }
2920 :
2921 :
2922 : /* If field names are desired then "clear" name buffer */
2923 : /* --------------------------------------------------- */
2924 6 : if (fieldlist != NULL)
2925 : {
2926 6 : fieldlist[0] = 0;
2927 : }
2928 :
2929 :
2930 : /* Begin loop through mapping entries in metadata */
2931 : /* ---------------------------------------------- */
2932 : while (1)
2933 : {
2934 : /* Search for OBJECT string */
2935 : /* ------------------------ */
2936 110 : metaptrs[0] = strstr(metaptrs[0], "\t\tOBJECT=");
2937 :
2938 :
2939 : /* If found within "Data" Field metadata section .. */
2940 : /* ------------------------------------------------ */
2941 110 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
2942 : {
2943 : /* Get Fieldnames (if desired) */
2944 : /* --------------------------- */
2945 104 : if (fieldlist != NULL)
2946 : {
2947 : /* Check 1st for old meta data then new */
2948 : /* ------------------------------------ */
2949 104 : EHgetmetavalue(metaptrs, "OBJECT", utlstr);
2950 :
2951 : /*
2952 : * If OBJECT value begins with double quote then old
2953 : * metadata, field name is OBJECT value. Otherwise
2954 : * search for "DataFieldName" string
2955 : */
2956 :
2957 104 : if (utlstr[0] != '"')
2958 : {
2959 104 : strcpy(utlstr, "\t\t\t\t");
2960 104 : strcat(utlstr, "DataFieldName");
2961 104 : strcat(utlstr, "=");
2962 104 : metaptrs[0] = strstr(metaptrs[0], utlstr);
2963 104 : EHgetmetavalue(metaptrs, "DataFieldName", utlstr);
2964 : }
2965 :
2966 : /* Strip off double quotes */
2967 : /* ----------------------- */
2968 104 : REMQUOTE(utlstr);
2969 :
2970 :
2971 : /* Add to fieldlist */
2972 : /* ---------------- */
2973 104 : if (nFld > 0)
2974 : {
2975 98 : strcat(fieldlist, ",");
2976 : }
2977 104 : strcat(fieldlist, utlstr);
2978 :
2979 : }
2980 : /* Get Numbertype */
2981 104 : if (numbertype != NULL)
2982 : {
2983 104 : EHgetmetavalue(metaptrs, "DataType", utlstr);
2984 104 : numbertype[nFld] = EHnumstr(utlstr);
2985 : }
2986 : /*
2987 : * Get Rank (if desired) by counting # of dimensions in
2988 : * "DimList" string
2989 : */
2990 104 : if (rank != NULL)
2991 : {
2992 104 : EHgetmetavalue(metaptrs, "DimList", utlstr);
2993 104 : rank[nFld] = EHparsestr(utlstr, ',', ptr, CPL_ARRAYSIZE(ptr), slen, CPL_ARRAYSIZE(slen));
2994 104 : if (rank[nFld] < 0)
2995 : {
2996 0 : status = -1;
2997 0 : break;
2998 : }
2999 : }
3000 : /* Increment number of fields */
3001 104 : nFld++;
3002 : }
3003 : else
3004 : /* No more fields found */
3005 : {
3006 : break;
3007 : }
3008 : }
3009 6 : free(metabuf);
3010 : }
3011 : }
3012 :
3013 : /* Set nFld to -1 if error status exists */
3014 : /* ------------------------------------- */
3015 6 : if (status == -1)
3016 : {
3017 0 : nFld = -1;
3018 : }
3019 6 : free(utlstr);
3020 6 : return (nFld);
3021 : }
3022 :
3023 :
3024 :
3025 :
3026 :
3027 : /*----------------------------------------------------------------------------|
3028 : | BEGIN_PROLOG |
3029 : | |
3030 : | FUNCTION: GDnentries |
3031 : | |
3032 : | DESCRIPTION: Returns number of entries and descriptive string buffer |
3033 : | size for a specified entity. |
3034 : | |
3035 : | |
3036 : | Return Value Type Units Description |
3037 : | ============ ====== ========= ===================================== |
3038 : | nEntries int32 Number of entries |
3039 : | |
3040 : | INPUTS: |
3041 : | gridID int32 grid structure ID |
3042 : | entrycode int32 Entry code |
3043 : | HDFE_NENTDIM (0) |
3044 : | HDFE_NENTDFLD (4) |
3045 : | |
3046 : | |
3047 : | OUTPUTS: |
3048 : | strbufsize int32 Length of comma-separated list |
3049 : | (Does not include null-terminator |
3050 : | |
3051 : | NOTES: |
3052 : | |
3053 : | |
3054 : | Date Programmer Description |
3055 : | ====== ============ ================================================= |
3056 : | Jun 96 Joel Gales Original Programmer |
3057 : | Aug 96 Joel Gales Make metadata ODL compliant |
3058 : | Feb 97 Joel Gales Set nEntries to -1 if status = -1 |
3059 : | |
3060 : | END_PROLOG |
3061 : -----------------------------------------------------------------------------*/
3062 : int32
3063 58 : GDnentries(int32 gridID, int32 entrycode, int32 * strbufsize)
3064 :
3065 : {
3066 : intn status; /* routine return status variable */
3067 : intn i; /* Loop index */
3068 :
3069 : int32 fid; /* HDF-EOS file ID */
3070 : int32 sdInterfaceID; /* HDF SDS interface ID */
3071 : int32 gdVgrpID; /* Grid root Vgroup ID */
3072 58 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
3073 58 : int32 nEntries = 0; /* Number of entries */
3074 : int32 metaflag; /* Old (0), New (1) metadata flag) */
3075 58 : int32 nVal = 0; /* Number of strings to search for */
3076 :
3077 58 : char *metabuf = NULL; /* Pointer to structural metadata (SM) */
3078 58 : char *metaptrs[2] = {NULL, NULL};/* Pointers to begin and end of SM section */
3079 : char gridname[80]; /* Grid Name */
3080 : char *utlstr;/* Utility string */
3081 : char valName[2][32]; /* Strings to search for */
3082 :
3083 58 : memset(valName, 0, sizeof(valName));
3084 :
3085 : /* Allocate space for utility string */
3086 : /* --------------------------------- */
3087 58 : utlstr = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
3088 58 : if(utlstr == NULL)
3089 : {
3090 0 : HEpush(DFE_NOSPACE,"GDnentries", __FILE__, __LINE__);
3091 0 : return(-1);
3092 : }
3093 58 : status = GDchkgdid(gridID, "GDnentries", &fid, &sdInterfaceID, &gdVgrpID);
3094 :
3095 58 : if (status == 0)
3096 : {
3097 : /* Get grid name */
3098 58 : int gID = gridID % idOffset;
3099 58 : if (gID >= NGRID)
3100 : {
3101 0 : free(utlstr);
3102 0 : return -1;
3103 : }
3104 :
3105 58 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
3106 :
3107 : /* Zero out string buffer size */
3108 58 : *strbufsize = 0;
3109 :
3110 :
3111 : /*
3112 : * Get pointer to relevant section within SM and Get names of
3113 : * metadata strings to inquire about
3114 : */
3115 58 : switch (entrycode)
3116 : {
3117 52 : case HDFE_NENTDIM:
3118 : {
3119 52 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
3120 : "Dimension", metaptrs);
3121 52 : if(metabuf == NULL)
3122 : {
3123 0 : free(utlstr);
3124 0 : return(-1);
3125 : }
3126 :
3127 52 : nVal = 1;
3128 52 : strcpy(&valName[0][0], "DimensionName");
3129 : }
3130 52 : break;
3131 :
3132 6 : case HDFE_NENTDFLD:
3133 : {
3134 6 : metabuf = (char *) EHmetagroup(sdInterfaceID, gridname, "g",
3135 : "DataField", metaptrs);
3136 6 : if(metabuf == NULL)
3137 : {
3138 0 : free(utlstr);
3139 0 : return(-1);
3140 : }
3141 :
3142 6 : nVal = 1;
3143 6 : strcpy(&valName[0][0], "DataFieldName");
3144 : }
3145 6 : break;
3146 : }
3147 :
3148 58 : if (!metabuf || metaptrs[0] == NULL)
3149 : {
3150 0 : free(metabuf);
3151 0 : free(utlstr);
3152 0 : return -1;
3153 : }
3154 :
3155 : /*
3156 : * Check for presence of 'GROUP="' string If found then old metadata,
3157 : * search on OBJECT string
3158 : */
3159 58 : metaflag = (strstr(metabuf, "GROUP=\"") == NULL) ? 1 : 0;
3160 58 : if (metaflag == 0)
3161 : {
3162 0 : nVal = 1;
3163 0 : strcpy(&valName[0][0], "\t\tOBJECT");
3164 : }
3165 :
3166 :
3167 : /* Begin loop through entries in metadata */
3168 : /* -------------------------------------- */
3169 : while (1)
3170 : {
3171 : /* Search for first string */
3172 164 : strcpy(utlstr, &valName[0][0]);
3173 164 : strcat(utlstr, "=");
3174 164 : metaptrs[0] = strstr(metaptrs[0], utlstr);
3175 :
3176 : /* If found within relevant metadata section ... */
3177 164 : if (metaptrs[0] < metaptrs[1] && metaptrs[0] != NULL)
3178 : {
3179 212 : for (i = 0; i < nVal; i++)
3180 : {
3181 : /*
3182 : * Get all string values Don't count quotes
3183 : */
3184 106 : EHgetmetavalue(metaptrs, &valName[i][0], utlstr);
3185 106 : if( utlstr[0] == '"' && utlstr[strlen(utlstr)-1] == '"' )
3186 6 : *strbufsize += (int32)strlen(utlstr) - 2;
3187 : else
3188 100 : *strbufsize += (int32)strlen(utlstr);
3189 : }
3190 : /* Increment number of entries */
3191 106 : nEntries++;
3192 :
3193 : /* Go to end of OBJECT */
3194 106 : metaptrs[0] = strstr(metaptrs[0], "END_OBJECT");
3195 : }
3196 : else
3197 : /* No more entries found */
3198 : {
3199 : break;
3200 : }
3201 : }
3202 58 : free(metabuf);
3203 :
3204 :
3205 : /* Count comma separators & slashes (if mappings) */
3206 : /* ---------------------------------------------- */
3207 58 : if (nEntries > 0)
3208 : {
3209 7 : *strbufsize += nEntries - 1;
3210 7 : *strbufsize += (nVal - 1) * nEntries;
3211 : }
3212 : }
3213 :
3214 :
3215 : /* Set nEntries to -1 if error status exists */
3216 : /* ----------------------------------------- */
3217 58 : if (status == -1)
3218 : {
3219 0 : nEntries = -1;
3220 : }
3221 :
3222 58 : free(utlstr);
3223 58 : return (nEntries);
3224 : }
3225 :
3226 :
3227 :
3228 :
3229 :
3230 : /*----------------------------------------------------------------------------|
3231 : | BEGIN_PROLOG |
3232 : | |
3233 : | FUNCTION: GDinqgrid |
3234 : | |
3235 : | DESCRIPTION: Returns number and names of grid structures in file |
3236 : | |
3237 : | |
3238 : | Return Value Type Units Description |
3239 : | ============ ====== ========= ===================================== |
3240 : | nGrid int32 Number of grid structures in file |
3241 : | |
3242 : | INPUTS: |
3243 : | filename char HDF-EOS filename |
3244 : | |
3245 : | OUTPUTS: |
3246 : | gridlist char List of grid names (comma-separated) |
3247 : | strbufsize int32 Length of gridlist |
3248 : | |
3249 : | NOTES: |
3250 : | |
3251 : | |
3252 : | Date Programmer Description |
3253 : | ====== ============ ================================================= |
3254 : | Jun 96 Joel Gales Original Programmer |
3255 : | |
3256 : | END_PROLOG |
3257 : -----------------------------------------------------------------------------*/
3258 : int32
3259 25 : GDinqgrid(const char *filename, char *gridlist, int32 * strbufsize)
3260 : {
3261 : int32 nGrid; /* Number of grid structures in file */
3262 :
3263 : /* Call "EHinquire" routine */
3264 : /* ------------------------ */
3265 25 : nGrid = EHinquire(filename, "GRID", gridlist, strbufsize);
3266 :
3267 25 : return (nGrid);
3268 : }
3269 :
3270 :
3271 :
3272 : /*----------------------------------------------------------------------------|
3273 : | BEGIN_PROLOG |
3274 : | |
3275 : | FUNCTION: GDgetfillvalue |
3276 : | |
3277 : | DESCRIPTION: Retrieves fill value for a specified field. |
3278 : | |
3279 : | |
3280 : | Return Value Type Units Description |
3281 : | ============ ====== ========= ===================================== |
3282 : | status intn return status (0) SUCCEED, (-1) FAIL |
3283 : | |
3284 : | INPUTS: |
3285 : | gridID int32 grid structure ID |
3286 : | fieldname char field name |
3287 : | |
3288 : | OUTPUTS: |
3289 : | fillval void fill value |
3290 : | |
3291 : | NOTES: |
3292 : | |
3293 : | |
3294 : | Date Programmer Description |
3295 : | ====== ============ ================================================= |
3296 : | Jun 96 Joel Gales Original Programmer |
3297 : | |
3298 : | END_PROLOG |
3299 : -----------------------------------------------------------------------------*/
3300 : intn
3301 2 : GDgetfillvalue(int32 gridID, const char *fieldname, VOIDP fillval)
3302 : {
3303 : intn status; /* routine return status variable */
3304 :
3305 : int32 nt; /* Number type */
3306 : int32 dims[8]; /* Dimensions array */
3307 : int32 dum; /* Dummy variable */
3308 :
3309 : char name[80]; /* Fill value "attribute" name */
3310 :
3311 2 : status = GDchkgdid(gridID, "GDgetfillvalue", &dum, &dum, &dum);
3312 :
3313 : /* Check for valid grid ID */
3314 2 : if (status == 0)
3315 : {
3316 : /* Get field info */
3317 1 : status = GDfieldinfo(gridID, fieldname, &dum, dims, &nt, NULL);
3318 :
3319 1 : if (status == 0)
3320 : {
3321 : /* Read fill value attribute */
3322 1 : strcpy(name, "_FV_");
3323 1 : strcat(name, fieldname);
3324 1 : status = GDreadattr(gridID, name, fillval);
3325 : }
3326 : else
3327 : {
3328 0 : HEpush(DFE_GENAPP, "GDgetfillvalue", __FILE__, __LINE__);
3329 0 : HEreport("Fieldname \"%s\" does not exist.\n", fieldname);
3330 : }
3331 :
3332 : }
3333 2 : return (status);
3334 : }
3335 :
3336 :
3337 :
3338 :
3339 :
3340 : /*----------------------------------------------------------------------------|
3341 : | BEGIN_PROLOG |
3342 : | |
3343 : | FUNCTION: GDdetach |
3344 : | |
3345 : | DESCRIPTION: Detaches from grid interface and performs file housekeeping. |
3346 : | |
3347 : | |
3348 : | Return Value Type Units Description |
3349 : | ============ ====== ========= ===================================== |
3350 : | status intn return status (0) SUCCEED, (-1) FAIL |
3351 : | |
3352 : | INPUTS: |
3353 : | gridID int32 grid structure ID |
3354 : | |
3355 : | |
3356 : | OUTPUTS: |
3357 : | None |
3358 : | |
3359 : | NOTES: |
3360 : | |
3361 : | |
3362 : | Date Programmer Description |
3363 : | ====== ============ ================================================= |
3364 : | Jun 96 Joel Gales Original Programmer |
3365 : | Sep 96 Joel Gales Setup dim names for SDsetdimname in dimbuf1 rather |
3366 : | that utlstr |
3367 : | Oct 96 Joel Gales Detach Grid Vgroups |
3368 : | Oct 96 Joel Gales "Detach" from SDS |
3369 : | Nov 96 Joel Gales Call GDchkgdid to check for proper grid ID |
3370 : | Dec 96 Joel Gales Add multiple vertical subsetting garbage collection |
3371 : | Oct 98 Abe Taaheri Added GDXRegion[k]->DimNamePtr[i] =0; after freeing |
3372 : | memory |
3373 : | Sep 99 Abe Taaheri Changed memcpy to memmove because of overlapping |
3374 : | source and destination for GDXSDcomb, nameptr, and |
3375 : | dimptr. memcpy may cause unexpected results. |
3376 : | |
3377 : | END_PROLOG |
3378 : -----------------------------------------------------------------------------*/
3379 : intn
3380 7 : GDdetach(int32 gridID)
3381 :
3382 : {
3383 : intn i; /* Loop index */
3384 : intn k; /* Loop index */
3385 7 : intn status = 0; /* routine return status variable */
3386 :
3387 : int32 sdInterfaceID; /* SDS interface ID */
3388 : int32 gID; /* Grid ID - offset */
3389 7 : int32 idOffset = GDIDOFFSET; /* Grid ID offset */
3390 : int32 dum; /* Dummy variable */
3391 :
3392 : char gridname[VGNAMELENMAX + 1]; /* Grid name */
3393 :
3394 :
3395 7 : status = GDchkgdid(gridID, "GDdetach", &dum, &sdInterfaceID, &dum);
3396 :
3397 7 : if (status == 0)
3398 : {
3399 7 : gID = gridID % idOffset;
3400 7 : if (gID >= NGRID)
3401 : {
3402 0 : return -1;
3403 : }
3404 7 : VgetnameSafe(GDXGrid[gID].IDTable, gridname, sizeof(gridname));
3405 :
3406 :
3407 : /* "Detach" from previously attached SDSs */
3408 : /* -------------------------------------- */
3409 10 : for (k = 0; k < GDXGrid[gID].nSDS; k++)
3410 : {
3411 3 : SDendaccess(GDXGrid[gID].sdsID[k]);
3412 : }
3413 7 : free(GDXGrid[gID].sdsID);
3414 7 : GDXGrid[gID].sdsID = 0;
3415 7 : GDXGrid[gID].nSDS = 0;
3416 :
3417 :
3418 :
3419 : /* Detach Grid Vgroups */
3420 : /* ------------------- */
3421 7 : Vdetach(GDXGrid[gID].VIDTable[0]);
3422 7 : Vdetach(GDXGrid[gID].VIDTable[1]);
3423 7 : Vdetach(GDXGrid[gID].IDTable);
3424 :
3425 7 : GDXGrid[gID].active = 0;
3426 7 : GDXGrid[gID].VIDTable[0] = 0;
3427 7 : GDXGrid[gID].VIDTable[1] = 0;
3428 7 : GDXGrid[gID].IDTable = 0;
3429 7 : GDXGrid[gID].fid = 0;
3430 :
3431 :
3432 :
3433 :
3434 : /* Free Region Pointers */
3435 : /* -------------------- */
3436 1799 : for (k = 0; k < NGRIDREGN; k++)
3437 : {
3438 1792 : if (GDXRegion[k] != 0 &&
3439 0 : GDXRegion[k]->gridID == gridID)
3440 : {
3441 0 : for (i = 0; i < 8; i++)
3442 : {
3443 0 : if (GDXRegion[k]->DimNamePtr[i] != 0)
3444 : {
3445 0 : free(GDXRegion[k]->DimNamePtr[i]);
3446 0 : GDXRegion[k]->DimNamePtr[i] = 0;
3447 : }
3448 : }
3449 :
3450 0 : free(GDXRegion[k]);
3451 0 : GDXRegion[k] = 0;
3452 : }
3453 : }
3454 : }
3455 7 : return (status);
3456 : }
3457 :
3458 :
3459 : /*----------------------------------------------------------------------------|
3460 : | BEGIN_PROLOG |
3461 : | |
3462 : | FUNCTION: GDclose |
3463 : | |
3464 : | DESCRIPTION: Closes file. |
3465 : | |
3466 : | |
3467 : | Return Value Type Units Description |
3468 : | ============ ====== ========= ===================================== |
3469 : | status intn return status (0) SUCCEED, (-1) FAIL |
3470 : | |
3471 : | INPUTS: |
3472 : | fid int32 File ID |
3473 : | |
3474 : | |
3475 : | OUTPUTS: |
3476 : | None |
3477 : | |
3478 : | NOTES: |
3479 : | |
3480 : | |
3481 : | Date Programmer Description |
3482 : | ====== ============ ================================================= |
3483 : | Jun 96 Joel Gales Original Programmer |
3484 : | |
3485 : | END_PROLOG |
3486 : -----------------------------------------------------------------------------*/
3487 : intn
3488 20 : GDclose(int32 fid)
3489 :
3490 : {
3491 20 : intn status = 0; /* routine return status variable */
3492 :
3493 : /* Call EHclose to perform file close */
3494 : /* ---------------------------------- */
3495 20 : status = EHclose(fid);
3496 :
3497 20 : return (status);
3498 : }
3499 :
3500 :
3501 : /*----------------------------------------------------------------------------|
3502 : | BEGIN_PROLOG |
3503 : | |
3504 : | FUNCTION: GDgetdefaults |
3505 : | |
3506 : | DESCRIPTION: |
3507 : | |
3508 : | |
3509 : | Return Value Type Units Description |
3510 : | ============ ====== ========= ===================================== |
3511 : | status intn return status (0) SUCCEED, (-1) FAIL |
3512 : | |
3513 : | INPUTS: |
3514 : | projcode int32 GCTP projection code |
3515 : | zonecode int32 UTM zone code |
3516 : | projparm float64 Projection parameters |
3517 : | spherecode int32 GCTP spheroid code |
3518 : | upleftpt float64 upper left corner coordinates |
3519 : | lowrightpt float64 lower right corner coordinates |
3520 : | |
3521 : | |
3522 : | OUTPUTS: |
3523 : | upleftpt float64 upper left corner coordinates |
3524 : | lowrightpt float64 lower right corner coordinates |
3525 : | |
3526 : | NOTES: |
3527 : | |
3528 : | |
3529 : | Date Programmer Description |
3530 : | ====== ============ ================================================= |
3531 : | Aug 96 Joel Gales Original Programmer |
3532 : | Sep 96 Raj Gejjaga Fixed bugs in Polar Stereographic and Goode | | Homolosine default calculations. |
3533 : | Sep 96 Raj Gejjaga Added code to compute default boundary points |
3534 : | for Lambert Azimuthal Polar and Equatorial |
3535 : | projections. |
3536 : | Feb 97 Raj Gejjaga Added code to compute default boundary points |
3537 : | for Integerized Sinusoidal Grid. Added error |
3538 : | handling code. |
3539 : | Jun 00 Abe Taaheri Added support for EASE grid |
3540 : | |
3541 : | END_PROLOG |
3542 : -----------------------------------------------------------------------------*/
3543 : static intn
3544 0 : GDgetdefaults(int32 projcode, int32 zonecode, float64 projparm[],
3545 : int32 spherecode, float64 upleftpt[], float64 lowrightpt[])
3546 : {
3547 0 : int32 errorcode = 0, status = 0;
3548 : int32(*for_trans[100]) (double, double, double*, double*);
3549 :
3550 : float64 lon, lat, plat, x, y;
3551 : float64 plon, tlon, llon, rlon, pplon, LLon, LLat, RLon, RLat;
3552 :
3553 :
3554 : /* invoke GCTP initialization routine */
3555 : /* ---------------------------------- */
3556 0 : for_init(projcode, zonecode, projparm, spherecode, NULL, NULL,
3557 : &errorcode, for_trans);
3558 :
3559 : /* Report error if any */
3560 : /* ------------------- */
3561 0 : if (errorcode != 0)
3562 : {
3563 0 : status = -1;
3564 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3565 0 : HEreport("GCTP Error: %d\n", errorcode);
3566 0 : return (status);
3567 : }
3568 :
3569 : /* Compute Default Boundary Points for EASE Grid */
3570 : /* Use Global coverage */
3571 : /* ------------------------------------------------------ */
3572 0 : if (projcode == GCTP_BCEA &&
3573 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3574 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3575 : {
3576 0 : upleftpt[0] = EHconvAng(EASE_GRID_DEFAULT_UPLEFT_LON, HDFE_DEG_DMS);
3577 0 : upleftpt[1] = EHconvAng(EASE_GRID_DEFAULT_UPLEFT_LAT, HDFE_DEG_DMS);
3578 0 : lowrightpt[0] = EHconvAng(EASE_GRID_DEFAULT_LOWRGT_LON, HDFE_DEG_DMS);
3579 0 : lowrightpt[1] = EHconvAng(EASE_GRID_DEFAULT_LOWRGT_LAT, HDFE_DEG_DMS);
3580 : }
3581 :
3582 : /* Compute Default Boundary Points for CEA */
3583 : /* --------------------------------------------*/
3584 0 : if (projcode == GCTP_CEA &&
3585 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3586 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3587 : {
3588 0 : LLon = EHconvAng(EASE_GRID_DEFAULT_UPLEFT_LON, HDFE_DEG_RAD);
3589 0 : LLat = EHconvAng(EASE_GRID_DEFAULT_UPLEFT_LAT, HDFE_DEG_RAD);
3590 0 : RLon = EHconvAng(EASE_GRID_DEFAULT_LOWRGT_LON, HDFE_DEG_RAD);
3591 0 : RLat = EHconvAng(EASE_GRID_DEFAULT_LOWRGT_LAT, HDFE_DEG_RAD);
3592 :
3593 0 : errorcode = for_trans[projcode] (LLon, LLat, &x, &y);
3594 0 : if (errorcode != 0)
3595 : {
3596 0 : status = -1;
3597 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3598 0 : HEreport("GCTP Error: %d\n", errorcode);
3599 0 : return (status);
3600 : }
3601 0 : upleftpt[0] = x;
3602 0 : upleftpt[1] = y;
3603 :
3604 0 : errorcode = for_trans[projcode] (RLon, RLat, &x, &y);
3605 0 : if (errorcode != 0)
3606 : {
3607 0 : status = -1;
3608 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3609 0 : HEreport("GCTP Error: %d\n", errorcode);
3610 0 : return (status);
3611 : }
3612 0 : lowrightpt[0] = x;
3613 0 : lowrightpt[1] = y;
3614 :
3615 : }
3616 :
3617 :
3618 : /* Compute Default Boundary Points for Polar Sterographic */
3619 : /* ------------------------------------------------------ */
3620 0 : if (projcode == GCTP_PS &&
3621 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3622 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3623 : {
3624 : /*
3625 : * Convert the longitude and latitude from the DMS to decimal degree
3626 : * format.
3627 : */
3628 0 : plon = EHconvAng(projparm[4], HDFE_DMS_DEG);
3629 0 : plat = EHconvAng(projparm[5], HDFE_DMS_DEG);
3630 :
3631 : /*
3632 : * Compute the longitudes at 90, 180 and 270 degrees from the central
3633 : * longitude.
3634 : */
3635 :
3636 0 : if (plon <= 0.0)
3637 : {
3638 0 : tlon = 180.0 + plon;
3639 0 : pplon = plon + 360.0;
3640 : }
3641 : else
3642 : {
3643 0 : tlon = plon - 180.0;
3644 0 : pplon = plon;
3645 : }
3646 :
3647 0 : rlon = pplon + 90.0;
3648 0 : if (rlon > 360.0)
3649 0 : rlon = rlon - 360;
3650 :
3651 0 : if (rlon > 180.0)
3652 0 : rlon = rlon - 360.0;
3653 :
3654 0 : if (rlon <= 0.0)
3655 0 : llon = 180.0 + rlon;
3656 : else
3657 0 : llon = rlon - 180.0;
3658 :
3659 :
3660 : /* Convert all four longitudes from decimal degrees to radians */
3661 0 : plon = EHconvAng(plon, HDFE_DEG_RAD);
3662 0 : tlon = EHconvAng(tlon, HDFE_DEG_RAD);
3663 0 : llon = EHconvAng(llon, HDFE_DEG_RAD);
3664 0 : rlon = EHconvAng(rlon, HDFE_DEG_RAD);
3665 :
3666 0 : errorcode = for_trans[projcode] (llon, 0.0, &x, &y);
3667 0 : if (errorcode != 0)
3668 : {
3669 0 : status = -1;
3670 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3671 0 : HEreport("GCTP Error: %d\n", errorcode);
3672 0 : return (status);
3673 : }
3674 :
3675 0 : upleftpt[0] = x;
3676 :
3677 0 : errorcode = for_trans[projcode] (rlon, 0.0, &x, &y);
3678 0 : if (errorcode != 0)
3679 : {
3680 0 : status = -1;
3681 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3682 0 : HEreport("GCTP Error: %d\n", errorcode);
3683 0 : return (status);
3684 : }
3685 :
3686 0 : lowrightpt[0] = x;
3687 :
3688 : /*
3689 : * Compute the upperleft and lowright y values based on the south or
3690 : * north polar projection
3691 : */
3692 :
3693 0 : if (plat < 0.0)
3694 : {
3695 0 : errorcode = for_trans[projcode] (plon, 0.0, &x, &y);
3696 0 : if (errorcode != 0)
3697 : {
3698 0 : status = -1;
3699 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3700 0 : HEreport("GCTP Error: %d\n", errorcode);
3701 0 : return (status);
3702 : }
3703 :
3704 0 : upleftpt[1] = y;
3705 :
3706 0 : errorcode = for_trans[projcode] (tlon, 0.0, &x, &y);
3707 0 : if (errorcode != 0)
3708 : {
3709 0 : status = -1;
3710 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3711 0 : HEreport("GCTP Error: %d\n", errorcode);
3712 0 : return (status);
3713 : }
3714 :
3715 0 : lowrightpt[1] = y;
3716 :
3717 : }
3718 : else
3719 : {
3720 0 : errorcode = for_trans[projcode] (tlon, 0.0, &x, &y);
3721 0 : if (errorcode != 0)
3722 : {
3723 0 : status = -1;
3724 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3725 0 : HEreport("GCTP Error: %d\n", errorcode);
3726 0 : return (status);
3727 : }
3728 :
3729 0 : upleftpt[1] = y;
3730 :
3731 0 : errorcode = for_trans[projcode] (plon, 0.0, &x, &y);
3732 0 : if (errorcode != 0)
3733 : {
3734 0 : status = -1;
3735 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3736 0 : HEreport("GCTP Error: %d\n", errorcode);
3737 0 : return (status);
3738 : }
3739 :
3740 0 : lowrightpt[1] = y;
3741 :
3742 : }
3743 : }
3744 :
3745 :
3746 : /* Compute Default Boundary Points for Goode Homolosine */
3747 : /* ---------------------------------------------------- */
3748 0 : if (projcode == GCTP_GOOD &&
3749 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3750 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3751 : {
3752 0 : lon = EHconvAng(-180, HDFE_DEG_RAD);
3753 0 : lat = 0.0;
3754 :
3755 0 : errorcode = for_trans[projcode] (lon, lat, &x, &y);
3756 0 : if (errorcode != 0)
3757 : {
3758 0 : status = -1;
3759 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3760 0 : HEreport("GCTP Error: %d\n", errorcode);
3761 0 : return (status);
3762 : }
3763 :
3764 0 : upleftpt[0] = -fabs(x);
3765 0 : lowrightpt[0] = +fabs(x);
3766 :
3767 0 : lat = EHconvAng(90, HDFE_DEG_RAD);
3768 :
3769 0 : errorcode = for_trans[projcode] (lon, lat, &x, &y);
3770 0 : if (errorcode != 0)
3771 : {
3772 0 : status = -1;
3773 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3774 0 : HEreport("GCTP Error: %d\n", errorcode);
3775 0 : return (status);
3776 : }
3777 :
3778 0 : upleftpt[1] = +fabs(y);
3779 0 : lowrightpt[1] = -fabs(y);
3780 : }
3781 :
3782 : /* Compute Default Boundary Points for Lambert Azimuthal */
3783 : /* ----------------------------------------------------- */
3784 0 : if (projcode == GCTP_LAMAZ &&
3785 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3786 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3787 : {
3788 : /*
3789 : * Convert the longitude and latitude from the DMS to decimal degree
3790 : * format.
3791 : */
3792 0 : plon = EHconvAng(projparm[4], HDFE_DMS_DEG);
3793 0 : plat = EHconvAng(projparm[5], HDFE_DMS_DEG);
3794 :
3795 : /*
3796 : * Compute the longitudes at 90, 180 and 270 degrees from the central
3797 : * longitude.
3798 : */
3799 :
3800 0 : if (plon <= 0.0)
3801 : {
3802 0 : tlon = 180.0 + plon;
3803 0 : pplon = plon + 360.0;
3804 : }
3805 : else
3806 : {
3807 0 : tlon = plon - 180.0;
3808 0 : pplon = plon;
3809 : }
3810 :
3811 0 : rlon = pplon + 90.0;
3812 0 : if (rlon > 360.0)
3813 0 : rlon = rlon - 360;
3814 :
3815 0 : if (rlon > 180.0)
3816 0 : rlon = rlon - 360.0;
3817 :
3818 0 : if (rlon <= 0.0)
3819 0 : llon = 180.0 + rlon;
3820 : else
3821 0 : llon = rlon - 180.0;
3822 :
3823 : /* Convert all four longitudes from decimal degrees to radians */
3824 0 : plon = EHconvAng(plon, HDFE_DEG_RAD);
3825 0 : tlon = EHconvAng(tlon, HDFE_DEG_RAD);
3826 0 : llon = EHconvAng(llon, HDFE_DEG_RAD);
3827 0 : rlon = EHconvAng(rlon, HDFE_DEG_RAD);
3828 :
3829 0 : errorcode = for_trans[projcode] (llon, 0.0, &x, &y);
3830 0 : if (errorcode != 0)
3831 : {
3832 0 : status = -1;
3833 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3834 0 : HEreport("GCTP Error: %d\n", errorcode);
3835 0 : return (status);
3836 : }
3837 :
3838 0 : upleftpt[0] = x;
3839 :
3840 0 : errorcode = for_trans[projcode] (rlon, 0.0, &x, &y);
3841 0 : if (errorcode != 0)
3842 : {
3843 0 : status = -1;
3844 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3845 0 : HEreport("GCTP Error: %d\n", errorcode);
3846 0 : return (status);
3847 : }
3848 :
3849 0 : lowrightpt[0] = x;
3850 :
3851 : /*
3852 : * Compute upperleft and lowerright values based on whether the
3853 : * projection is south polar, north polar or equatorial
3854 : */
3855 :
3856 0 : if (plat == -90.0)
3857 : {
3858 0 : errorcode = for_trans[projcode] (plon, 0.0, &x, &y);
3859 0 : if (errorcode != 0)
3860 : {
3861 0 : status = -1;
3862 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3863 0 : HEreport("GCTP Error: %d\n", errorcode);
3864 0 : return (status);
3865 : }
3866 :
3867 0 : upleftpt[1] = y;
3868 :
3869 0 : errorcode = for_trans[projcode] (tlon, 0.0, &x, &y);
3870 0 : if (errorcode != 0)
3871 : {
3872 0 : status = -1;
3873 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3874 0 : HEreport("GCTP Error: %d\n", errorcode);
3875 0 : return (status);
3876 : }
3877 :
3878 0 : lowrightpt[1] = y;
3879 : }
3880 0 : else if (plat == 90.0)
3881 : {
3882 0 : errorcode = for_trans[projcode] (tlon, 0.0, &x, &y);
3883 0 : if (errorcode != 0)
3884 : {
3885 0 : status = -1;
3886 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3887 0 : HEreport("GCTP Error: %d\n", errorcode);
3888 0 : return (status);
3889 : }
3890 :
3891 0 : upleftpt[1] = y;
3892 :
3893 0 : errorcode = for_trans[projcode] (plon, 0.0, &x, &y);
3894 0 : if (errorcode != 0)
3895 : {
3896 0 : status = -1;
3897 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3898 0 : HEreport("GCTP Error: %d\n", errorcode);
3899 0 : return (status);
3900 : }
3901 :
3902 0 : lowrightpt[1] = y;
3903 : }
3904 : else
3905 : {
3906 0 : lat = EHconvAng(90, HDFE_DEG_RAD);
3907 0 : errorcode = for_trans[projcode] (plon, lat, &x, &y);
3908 0 : if (errorcode != 0)
3909 : {
3910 0 : status = -1;
3911 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3912 0 : HEreport("GCTP Error: %d\n", errorcode);
3913 0 : return (status);
3914 : }
3915 :
3916 0 : upleftpt[1] = y;
3917 :
3918 0 : lat = EHconvAng(-90, HDFE_DEG_RAD);
3919 0 : errorcode = for_trans[projcode] (plon, lat, &x, &y);
3920 0 : if (errorcode != 0)
3921 : {
3922 0 : status = -1;
3923 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3924 0 : HEreport("GCTP Error: %d\n", errorcode);
3925 0 : return (status);
3926 : }
3927 :
3928 0 : lowrightpt[1] = y;
3929 : }
3930 : }
3931 :
3932 : /* Compute Default Boundary Points for Integerized Sinusoidal Grid */
3933 : /* --------------------------------------------------------------- */
3934 0 : if (((projcode == GCTP_ISINUS) || (projcode == GCTP_ISINUS1)) &&
3935 0 : upleftpt[0] == 0 && upleftpt[1] == 0 &&
3936 0 : lowrightpt[0] == 0 && lowrightpt[1] == 0)
3937 : {
3938 : /*
3939 : * Convert the longitude and latitude from the DMS to decimal degree
3940 : * format.
3941 : */
3942 0 : plon = EHconvAng(projparm[4], HDFE_DMS_DEG);
3943 : /*plat = EHconvAng(projparm[5], HDFE_DMS_DEG); */
3944 :
3945 : /*
3946 : * Compute the longitudes at 90, 180 and 270 degrees from the central
3947 : * longitude.
3948 : */
3949 :
3950 0 : if (plon <= 0.0)
3951 : {
3952 : //tlon = 180.0 + plon;
3953 0 : pplon = plon + 360.0;
3954 : }
3955 : else
3956 : {
3957 : //tlon = plon - 180.0;
3958 0 : pplon = plon;
3959 : }
3960 :
3961 0 : rlon = pplon + 90.0;
3962 0 : if (rlon > 360.0)
3963 0 : rlon = rlon - 360;
3964 :
3965 0 : if (rlon > 180.0)
3966 0 : rlon = rlon - 360.0;
3967 :
3968 0 : if (rlon <= 0.0)
3969 0 : llon = 180.0 + rlon;
3970 : else
3971 0 : llon = rlon - 180.0;
3972 :
3973 : /* Convert all four longitudes from decimal degrees to radians */
3974 0 : plon = EHconvAng(plon, HDFE_DEG_RAD);
3975 : //tlon = EHconvAng(tlon, HDFE_DEG_RAD);
3976 0 : llon = EHconvAng(llon, HDFE_DEG_RAD);
3977 0 : rlon = EHconvAng(rlon, HDFE_DEG_RAD);
3978 :
3979 0 : errorcode = for_trans[projcode] (llon, 0.0, &x, &y);
3980 0 : if (errorcode != 0)
3981 : {
3982 0 : status = -1;
3983 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3984 0 : HEreport("GCTP Error: %d\n", errorcode);
3985 0 : return (status);
3986 : }
3987 :
3988 0 : upleftpt[0] = x;
3989 :
3990 0 : errorcode = for_trans[projcode] (rlon, 0.0, &x, &y);
3991 0 : if (errorcode != 0)
3992 : {
3993 0 : status = -1;
3994 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
3995 0 : HEreport("GCTP Error: %d\n", errorcode);
3996 0 : return (status);
3997 : }
3998 :
3999 0 : lowrightpt[0] = x;
4000 :
4001 0 : lat = EHconvAng(90, HDFE_DEG_RAD);
4002 0 : errorcode = for_trans[projcode] (plon, lat, &x, &y);
4003 0 : if (errorcode != 0)
4004 : {
4005 0 : status = -1;
4006 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
4007 0 : HEreport("GCTP Error: %d\n", errorcode);
4008 0 : return (status);
4009 : }
4010 :
4011 0 : upleftpt[1] = y;
4012 :
4013 0 : lat = EHconvAng(-90, HDFE_DEG_RAD);
4014 0 : errorcode = for_trans[projcode] (plon, lat, &x, &y);
4015 0 : if (errorcode != 0)
4016 : {
4017 0 : status = -1;
4018 0 : HEpush(DFE_GENAPP, "GDgetdefaults", __FILE__, __LINE__);
4019 0 : HEreport("GCTP Error: %d\n", errorcode);
4020 0 : return (status);
4021 : }
4022 :
4023 0 : lowrightpt[1] = y;
4024 : }
4025 0 : return (errorcode);
4026 : }
4027 :
4028 : /*----------------------------------------------------------------------------|
4029 : | BEGIN_PROLOG |
4030 : | |
4031 : | FUNCTION: GDll2ij |
4032 : | |
4033 : | DESCRIPTION: |
4034 : | |
4035 : | |
4036 : | Return Value Type Units Description |
4037 : | ============ ====== ========= ===================================== |
4038 : | status intn return status (0) SUCCEED, (-1) FAIL |
4039 : | |
4040 : | INPUTS: |
4041 : | projcode int32 GCTP projection code |
4042 : | zonecode int32 UTM zone code |
4043 : | projparm float64 Projection parameters |
4044 : | spherecode int32 GCTP spheroid code |
4045 : | xdimsize int32 xdimsize from GDcreate |
4046 : | ydimsize int32 ydimsize from GDcreate |
4047 : | upleftpt float64 upper left corner coordinates |
4048 : | lowrightpt float64 lower right corner coordinates |
4049 : | npnts int32 number of lon-lat points |
4050 : | longitude float64 longitude array (radians) |
4051 : | latitude float64 latitude array (radians) |
4052 : | |
4053 : | OUTPUTS: |
4054 : | row int32 Row array |
4055 : | col int32 Column array |
4056 : | xval float64 X value array |
4057 : | yval float64 Y value array |
4058 : | |
4059 : | |
4060 : | NOTES: |
4061 : | |
4062 : | |
4063 : | Date Programmer Description |
4064 : | ====== ============ ================================================= |
4065 : | Jun 96 Joel Gales Original Programmer |
4066 : | Aug 96 Joel Gales Return x and y values if requested |
4067 : | Jun 00 Abe Taaheri Added support for EASE grid |
4068 : | |
4069 : | END_PROLOG |
4070 : -----------------------------------------------------------------------------*/
4071 : static intn
4072 0 : GDll2ij(int32 projcode, int32 zonecode, float64 projparm[],
4073 : int32 spherecode, int32 xdimsize, int32 ydimsize,
4074 : float64 upleftpt[], float64 lowrightpt[],
4075 : int32 npnts, float64 longitude[], float64 latitude[],
4076 : int32 row[], int32 col[], float64 xval[], float64 yval[])
4077 :
4078 :
4079 : {
4080 : intn i; /* Loop index */
4081 0 : intn status = 0; /* routine return status variable */
4082 :
4083 0 : int32 errorcode = 0; /* GCTP error code */
4084 : int32(*for_trans[100]) (double, double, double*, double*); /* GCTP function pointer */
4085 :
4086 : float64 xVal; /* Scaled x distance */
4087 : float64 yVal; /* Scaled y distance */
4088 : float64 xMtr; /* X value in meters from GCTP */
4089 : float64 yMtr; /* Y value in meters from GCTP */
4090 : float64 lonrad0; /* Longitude in radians of upleft point */
4091 0 : float64 latrad0 = 0; /* Latitude in radians of upleft point */
4092 : float64 lonrad; /* Longitude in radians of point */
4093 : float64 latrad; /* Latitude in radians of point */
4094 : float64 scaleX; /* X scale factor */
4095 : float64 scaleY; /* Y scale factor */
4096 0 : float64 xMtr0 = 0, xMtr1, yMtr0 = 0, yMtr1;
4097 : float64 lonrad1; /* Longitude in radians of lowright point */
4098 :
4099 : /* If projection not GEO call GCTP initialization routine */
4100 : /* ------------------------------------------------------ */
4101 0 : if (projcode != GCTP_GEO)
4102 : {
4103 0 : for_init(projcode, zonecode, projparm, spherecode, NULL, NULL,
4104 : &errorcode, for_trans);
4105 :
4106 : /* Report error if any */
4107 : /* ------------------- */
4108 0 : if (errorcode != 0)
4109 : {
4110 0 : status = -1;
4111 0 : HEpush(DFE_GENAPP, "GDll2ij", __FILE__, __LINE__);
4112 0 : HEreport("GCTP Error: %d\n", errorcode);
4113 : }
4114 : }
4115 :
4116 :
4117 0 : if (status == 0)
4118 : {
4119 : /* GEO projection */
4120 : /* -------------- */
4121 0 : if (projcode == GCTP_GEO)
4122 : {
4123 : /* Convert upleft and lowright X coords from DMS to radians */
4124 : /* -------------------------------------------------------- */
4125 0 : lonrad0 = EHconvAng(upleftpt[0], HDFE_DMS_RAD);
4126 0 : lonrad = EHconvAng(lowrightpt[0], HDFE_DMS_RAD);
4127 :
4128 : /* Compute x scale factor */
4129 : /* ---------------------- */
4130 0 : scaleX = (lonrad - lonrad0) / xdimsize;
4131 :
4132 :
4133 : /* Convert upleft and lowright Y coords from DMS to radians */
4134 : /* -------------------------------------------------------- */
4135 0 : latrad0 = EHconvAng(upleftpt[1], HDFE_DMS_RAD);
4136 0 : latrad = EHconvAng(lowrightpt[1], HDFE_DMS_RAD);
4137 :
4138 :
4139 : /* Compute y scale factor */
4140 : /* ---------------------- */
4141 0 : scaleY = (latrad - latrad0) / ydimsize;
4142 : }
4143 :
4144 : /* BCEA projection */
4145 : /* -------------- */
4146 0 : else if ( projcode == GCTP_BCEA)
4147 : {
4148 : /* Convert upleft and lowright X coords from DMS to radians */
4149 : /* -------------------------------------------------------- */
4150 :
4151 0 : lonrad0 = EHconvAng(upleftpt[0], HDFE_DMS_RAD);
4152 0 : lonrad = EHconvAng(lowrightpt[0], HDFE_DMS_RAD);
4153 :
4154 : /* Convert upleft and lowright Y coords from DMS to radians */
4155 : /* -------------------------------------------------------- */
4156 0 : latrad0 = EHconvAng(upleftpt[1], HDFE_DMS_RAD);
4157 0 : latrad = EHconvAng(lowrightpt[1], HDFE_DMS_RAD);
4158 :
4159 : /* Convert from lon/lat to meters(or whatever unit is, i.e unit
4160 : of r_major and r_minor) using GCTP */
4161 : /* ----------------------------------------- */
4162 0 : errorcode = for_trans[projcode] (lonrad0, latrad0, &xMtr0, &yMtr0);
4163 :
4164 :
4165 : /* Report error if any */
4166 : /* ------------------- */
4167 0 : if (errorcode != 0)
4168 : {
4169 0 : status = -1;
4170 0 : HEpush(DFE_GENAPP, "GDll2ij", __FILE__, __LINE__);
4171 0 : HEreport("GCTP Error: %d\n", errorcode);
4172 0 : return (status);
4173 : }
4174 :
4175 : /* Convert from lon/lat to meters(or whatever unit is, i.e unit
4176 : of r_major and r_minor) using GCTP */
4177 : /* ----------------------------------------- */
4178 0 : errorcode = for_trans[projcode] (lonrad, latrad, &xMtr1, &yMtr1);
4179 :
4180 :
4181 : /* Report error if any */
4182 : /* ------------------- */
4183 0 : if (errorcode != 0)
4184 : {
4185 0 : status = -1;
4186 0 : HEpush(DFE_GENAPP, "GDll2ij", __FILE__, __LINE__);
4187 0 : HEreport("GCTP Error: %d\n", errorcode);
4188 0 : return (status);
4189 : }
4190 :
4191 : /* Compute x scale factor */
4192 : /* ---------------------- */
4193 0 : scaleX = (xMtr1 - xMtr0) / xdimsize;
4194 :
4195 : /* Compute y scale factor */
4196 : /* ---------------------- */
4197 0 : scaleY = (yMtr1 - yMtr0) / ydimsize;
4198 : }
4199 : else
4200 : {
4201 : /* Non-GEO, Non_BCEA projections */
4202 : /* ---------------------------- */
4203 :
4204 : /* Compute x & y scale factors */
4205 : /* --------------------------- */
4206 0 : scaleX = (lowrightpt[0] - upleftpt[0]) / xdimsize;
4207 0 : scaleY = (lowrightpt[1] - upleftpt[1]) / ydimsize;
4208 : }
4209 :
4210 :
4211 :
4212 : /* Loop through all points */
4213 : /* ----------------------- */
4214 0 : for (i = 0; i < npnts; i++)
4215 : {
4216 : /* Convert lon & lat from decimal degrees to radians */
4217 : /* ------------------------------------------------- */
4218 0 : lonrad = EHconvAng(longitude[i], HDFE_DEG_RAD);
4219 0 : latrad = EHconvAng(latitude[i], HDFE_DEG_RAD);
4220 :
4221 :
4222 : /* GEO projection */
4223 : /* -------------- */
4224 0 : if (projcode == GCTP_GEO)
4225 : {
4226 : /* allow map to span dateline */
4227 0 : lonrad0 = EHconvAng(upleftpt[0], HDFE_DMS_RAD);
4228 0 : lonrad1 = EHconvAng(lowrightpt[0], HDFE_DMS_RAD);
4229 : /* if time-line is passed */
4230 0 : if(lonrad < lonrad1)
4231 : {
4232 0 : if (lonrad < lonrad0) lonrad += 2.0 * M_PI;
4233 0 : if (lonrad > lonrad1) lonrad -= 2.0 * M_PI;
4234 : }
4235 :
4236 : /* Compute scaled distance to point from origin */
4237 : /* -------------------------------------------- */
4238 0 : xVal = (lonrad - lonrad0) / scaleX;
4239 0 : yVal = (latrad - latrad0) / scaleY;
4240 : }
4241 : else
4242 : {
4243 : /* Convert from lon/lat to meters using GCTP */
4244 : /* ----------------------------------------- */
4245 0 : errorcode = for_trans[projcode] (lonrad, latrad, &xMtr, &yMtr);
4246 :
4247 :
4248 : /* Report error if any */
4249 : /* ------------------- */
4250 0 : if (errorcode != 0)
4251 : {
4252 : /*status = -1;
4253 : HEpush(DFE_GENAPP, "GDll2ij", __FILE__, __LINE__);
4254 : HEreport("GCTP Error: %d\n", errorcode);
4255 : return (status); */ /* Bruce Beaumont */
4256 0 : xVal = -2147483648.0; /* Bruce Beaumont */
4257 0 : yVal = -2147483648.0; /* Bruce Beaumont */
4258 : }/* (Note: MAXLONG is defined as 2147483647.0 in
4259 : function cproj.c of GCTP) */
4260 : else {
4261 : /* if projection is BCEA normalize x and y by cell size and
4262 : measure it from the upperleft corner of the grid */
4263 :
4264 : /* Compute scaled distance to point from origin */
4265 : /* -------------------------------------------- */
4266 0 : if( projcode == GCTP_BCEA)
4267 : {
4268 0 : xVal = (xMtr - xMtr0) / scaleX;
4269 0 : yVal = (yMtr - yMtr0) / scaleY;
4270 : }
4271 : else
4272 : {
4273 0 : xVal = (xMtr - upleftpt[0]) / scaleX;
4274 0 : yVal = (yMtr - upleftpt[1]) / scaleY;
4275 : }
4276 : }
4277 : }
4278 :
4279 :
4280 : /* Compute row and col from scaled distance */
4281 : /* ---------------------------------------- */
4282 0 : col[i] = (int32) xVal;
4283 0 : row[i] = (int32) yVal;
4284 :
4285 : /* Store scaled distances if requested */
4286 : /* ----------------------------------- */
4287 0 : if (xval != NULL)
4288 : {
4289 0 : xval[i] = xVal;
4290 : }
4291 :
4292 0 : if (yval != NULL)
4293 : {
4294 0 : yval[i] = yVal;
4295 : }
4296 : }
4297 : }
4298 0 : return (status);
4299 : }
4300 :
4301 : /*----------------------------------------------------------------------------|
4302 : | BEGIN_PROLOG |
4303 : | |
4304 : | FUNCTION: GDgetpixels |
4305 : | |
4306 : | DESCRIPTION: Finds row and columns for specified lon/lat values |
4307 : | |
4308 : | |
4309 : | Return Value Type Units Description |
4310 : | ============ ====== ========= ===================================== |
4311 : | status intn return status (0) SUCCEED, (-1) FAIL |
4312 : | |
4313 : | INPUTS: |
4314 : | gridID int32 Grid structure ID |
4315 : | nLonLat int32 Number of lonlat values |
4316 : | lonVal float64 dec deg Longitude values |
4317 : | latVal float64 dec deg Latitude values |
4318 : | |
4319 : | |
4320 : | OUTPUTS: |
4321 : | pixRow int32 Pixel rows |
4322 : | pixCol int32 Pixel columns |
4323 : | |
4324 : | NOTES: |
4325 : | |
4326 : | |
4327 : | Date Programmer Description |
4328 : | ====== ============ ================================================= |
4329 : | Aug 96 Joel Gales Original Programmer |
4330 : | Oct 96 Joel Gales Set row/col to -1 if outside boundary |
4331 : | Mar 97 Joel Gales Adjust row/col for CORNER pixel registration |
4332 : | |
4333 : | END_PROLOG |
4334 : -----------------------------------------------------------------------------*/
4335 : intn
4336 0 : GDgetpixels(int32 gridID, int32 nLonLat, float64 lonVal[], float64 latVal[],
4337 : int32 pixRow[], int32 pixCol[])
4338 : {
4339 : intn i; /* Loop index */
4340 0 : intn status = 0; /* routine return status variable */
4341 :
4342 : int32 fid; /* HDF-EOS file ID */
4343 : int32 sdInterfaceID; /* HDF SDS interface ID */
4344 : int32 gdVgrpID; /* Grid root Vgroup ID */
4345 :
4346 0 : int32 xdimsize = 0; /* Size of "XDim" */
4347 0 : int32 ydimsize = 0; /* Size of "YDim" */
4348 0 : int32 projcode = 0; /* GCTP projection code */
4349 0 : int32 zonecode = 0; /* Zone code */
4350 0 : int32 spherecode = 0; /* Sphere code */
4351 0 : int32 origincode = 0; /* Origin code */
4352 0 : int32 pixregcode = 0; /* Pixel registration code */
4353 :
4354 : float64 upleftpt[2];/* Upper left point */
4355 : float64 lowrightpt[2]; /* Lower right point */
4356 : float64 projparm[16]; /* Projection parameters */
4357 : float64 *xVal; /* Pointer to point x location values */
4358 : float64 *yVal; /* Pointer to point y location values */
4359 :
4360 :
4361 : /* Check for valid grid ID */
4362 : /* ----------------------- */
4363 0 : status = GDchkgdid(gridID, "GDgetpixels", &fid, &sdInterfaceID, &gdVgrpID);
4364 0 : if (status < 0)
4365 0 : return -1;
4366 :
4367 : /* Get grid info */
4368 : /* ------------- */
4369 0 : status = GDgridinfo(gridID, &xdimsize, &ydimsize,
4370 : upleftpt, lowrightpt);
4371 0 : if (status < 0)
4372 0 : return -1;
4373 :
4374 :
4375 : /* Get projection info */
4376 : /* ------------------- */
4377 0 : status = GDprojinfo(gridID, &projcode, &zonecode,
4378 : &spherecode, projparm);
4379 0 : if (status < 0)
4380 0 : return -1;
4381 :
4382 :
4383 : /* Get explicit upleftpt & lowrightpt if defaults are used */
4384 : /* ------------------------------------------------------- */
4385 0 : status = GDgetdefaults(projcode, zonecode, projparm, spherecode,
4386 : upleftpt, lowrightpt);
4387 0 : if (status < 0)
4388 0 : return -1;
4389 :
4390 :
4391 : /* Get pixel registration and origin info */
4392 : /* -------------------------------------- */
4393 0 : status = GDorigininfo(gridID, &origincode);
4394 0 : if (status < 0)
4395 0 : return -1;
4396 0 : status = GDpixreginfo(gridID, &pixregcode);
4397 0 : if (status < 0)
4398 0 : return -1;
4399 :
4400 :
4401 : /* Allocate space for x & y locations */
4402 : /* ---------------------------------- */
4403 0 : xVal = (float64 *) calloc(nLonLat, sizeof(float64));
4404 0 : if(xVal == NULL)
4405 : {
4406 0 : HEpush(DFE_NOSPACE,"GDgetpixels", __FILE__, __LINE__);
4407 0 : return(-1);
4408 : }
4409 0 : yVal = (float64 *) calloc(nLonLat, sizeof(float64));
4410 0 : if(yVal == NULL)
4411 : {
4412 0 : HEpush(DFE_NOSPACE,"GDgetpixels", __FILE__, __LINE__);
4413 0 : free(xVal);
4414 0 : return(-1);
4415 : }
4416 :
4417 :
4418 : /* Get pixRow, pixCol, xVal, & yVal */
4419 : /* -------------------------------- */
4420 0 : status = GDll2ij(projcode, zonecode, projparm, spherecode,
4421 : xdimsize, ydimsize, upleftpt, lowrightpt,
4422 : nLonLat, lonVal, latVal, pixRow, pixCol,
4423 : xVal, yVal);
4424 :
4425 :
4426 :
4427 : /* Loop through all lon/lat values */
4428 : /* ------------------------------- */
4429 0 : for (i = 0; i < nLonLat; i++)
4430 : {
4431 : /* Adjust columns & rows for "corner" registered grids */
4432 : /* --------------------------------------------------- */
4433 0 : if (pixregcode == HDFE_CORNER)
4434 : {
4435 0 : if (origincode == HDFE_GD_UL)
4436 : {
4437 0 : if (xVal[i] - pixCol[i] > 0.5)
4438 : {
4439 0 : ++pixCol[i];
4440 : }
4441 :
4442 0 : if (yVal[i] - pixRow[i] > 0.5)
4443 : {
4444 0 : ++pixRow[i];
4445 : }
4446 : }
4447 0 : else if (origincode == HDFE_GD_UR)
4448 : {
4449 0 : if (xVal[i] - pixCol[i] <= 0.5)
4450 : {
4451 0 : --pixCol[i];
4452 : }
4453 :
4454 0 : if (yVal[i] - pixRow[i] > 0.5)
4455 : {
4456 0 : ++pixRow[i];
4457 : }
4458 : }
4459 0 : else if (origincode == HDFE_GD_LL)
4460 : {
4461 0 : if (xVal[i] - pixCol[i] > 0.5)
4462 : {
4463 0 : ++pixCol[i];
4464 : }
4465 :
4466 0 : if (yVal[i] - pixRow[i] <= 0.5)
4467 : {
4468 0 : --pixRow[i];
4469 : }
4470 : }
4471 0 : else if (origincode == HDFE_GD_LR)
4472 : {
4473 0 : if (xVal[i] - pixCol[i] <= 0.5)
4474 : {
4475 0 : --pixCol[i];
4476 : }
4477 :
4478 0 : if (yVal[i] - pixRow[i] <= 0.5)
4479 : {
4480 0 : --pixRow[i];
4481 : }
4482 : }
4483 : }
4484 :
4485 :
4486 : /* If outside grid boundaries then set to -1 */
4487 : /* ----------------------------------------- */
4488 0 : if (pixCol[i] < 0 || pixCol[i] >= xdimsize ||
4489 0 : pixRow[i] < 0 || pixRow[i] >= ydimsize)
4490 : {
4491 0 : pixCol[i] = -1;
4492 0 : pixRow[i] = -1;
4493 : }
4494 : }
4495 0 : free(xVal);
4496 0 : free(yVal);
4497 :
4498 0 : return (status);
4499 : }
4500 :
4501 :
4502 :
4503 :
4504 :
4505 : /*----------------------------------------------------------------------------|
4506 : | BEGIN_PROLOG |
4507 : | |
4508 : | FUNCTION: GDgetpixvalues |
4509 : | |
4510 : | DESCRIPTION: Retrieves data from specified pixels. |
4511 : | |
4512 : | |
4513 : | Return Value Type Units Description |
4514 : | ============ ====== ========= ===================================== |
4515 : | size*nPixels int32 Size of data buffer |
4516 : | |
4517 : | INPUTS: |
4518 : | gridID int32 Grid structure ID |
4519 : | nPixels int32 Number of pixels |
4520 : | pixRow int32 Pixel row numbers |
4521 : | pixCol int32 Pixel column numbers |
4522 : | fieldname char Fieldname |
4523 : | |
4524 : | OUTPUTS: |
4525 : | buffer void Data buffer |
4526 : | |
4527 : | |
4528 : | NOTES: |
4529 : | |
4530 : | |
4531 : | Date Programmer Description |
4532 : | ====== ============ ================================================= |
4533 : | Aug 96 Joel Gales Original Programmer |
4534 : | Oct 96 Joel Gales Check for pixels outside boundaries (-1) |
4535 : | Mar 98 Abe Taaheri revised to reduce overhead for rechecking |
4536 : | for gridid, fieldname, etc in GDreadfield. |
4537 : | June 98 AT fixed bug with 2-dim field merged in 3-dim field |
4538 : | (for offset and count) |
4539 : | END_PROLOG |
4540 : -----------------------------------------------------------------------------*/
4541 : int32
4542 0 : GDgetpixvalues(int32 gridID, int32 nPixels, int32 pixRow[], int32 pixCol[],
4543 : const char *fieldname, VOIDP buffer)
4544 : {
4545 : intn i; /* Loop index */
4546 : intn j; /* Loop index */
4547 0 : intn status = 0; /* routine return status variable */
4548 :
4549 : int32 fid; /* HDF-EOS file ID */
4550 : int32 sdInterfaceID; /* HDF SDS interface ID */
4551 : int32 gdVgrpID; /* Grid root Vgroup ID */
4552 :
4553 : int32 start[8]; /* GDreadfield start array */
4554 : int32 edge[8]; /* GDreadfield edge array */
4555 : int32 dims[8]; /* Field dimensions */
4556 : int32 rank; /* Field rank */
4557 0 : int32 xdum = 0; /* Location of "XDim" within field list */
4558 0 : int32 ydum = 0; /* Location of "YDim" within field list */
4559 : int32 ntype; /* Field number type */
4560 0 : int32 origincode = 0; /* Origin code */
4561 : int32 bufOffset; /* Data buffer offset */
4562 0 : int32 size = 0; /* Size of returned data buffer for each
4563 : * value in bytes */
4564 0 : int32 offset[8] = {0}; /* I/O offset (start) */
4565 : int32 incr[8]; /* I/O increment (stride) */
4566 : int32 count[8]; /* I/O count (edge) */
4567 : int32 sdid; /* SDS ID */
4568 : int32 rankSDS; /* Rank of SDS */
4569 : int32 rankFld; /* Rank of field */
4570 : int32 dum; /* Dummy variable */
4571 0 : int32 mrgOffset = 0; /* Merged field offset */
4572 :
4573 : char *dimlist; /* Dimension list */
4574 :
4575 :
4576 :
4577 : /* Allocate space for dimlist */
4578 : /* --------------------------------- */
4579 0 : dimlist = (char *) calloc(UTLSTR_MAX_SIZE, sizeof(char));
4580 0 : if(dimlist == NULL)
4581 : {
4582 0 : HEpush(DFE_NOSPACE,"GDgetpixvalues", __FILE__, __LINE__);
4583 0 : return(-1);
4584 : }
4585 : /* Check for valid grid ID */
4586 : /* ----------------------- */
4587 0 : status = GDchkgdid(gridID, "GDgetpixvalues",
4588 : &fid, &sdInterfaceID, &gdVgrpID);
4589 :
4590 :
4591 0 : if (status == 0)
4592 : {
4593 : /* Get field list */
4594 : /* -------------- */
4595 0 : status = GDfieldinfo(gridID, fieldname, &rank, dims, &ntype, dimlist);
4596 :
4597 :
4598 : /* Check for "XDim" & "YDim" in dimension list */
4599 : /* ------------------------------------------- */
4600 0 : if (status == 0)
4601 : {
4602 0 : xdum = EHstrwithin("XDim", dimlist, ',');
4603 0 : ydum = EHstrwithin("YDim", dimlist, ',');
4604 :
4605 0 : if (xdum == -1)
4606 : {
4607 0 : status = -1;
4608 0 : HEpush(DFE_GENAPP, "GDgetpixvalues", __FILE__, __LINE__);
4609 0 : HEreport(
4610 : "\"XDim\" not present in dimlist for field: \"%s\".\n",
4611 : fieldname);
4612 : }
4613 :
4614 :
4615 0 : if (ydum == -1)
4616 : {
4617 0 : status = -1;
4618 0 : HEpush(DFE_GENAPP, "GDgetpixvalues", __FILE__, __LINE__);
4619 0 : HEreport(
4620 : "\"YDim\" not present in dimlist for field: \"%s\".\n",
4621 : fieldname);
4622 : }
4623 : }
4624 : else
4625 : {
4626 0 : status = -1;
4627 0 : HEpush(DFE_GENAPP, "GDgetpixvalues", __FILE__, __LINE__);
4628 0 : HEreport("Fieldname \"%s\" not found.\n", fieldname);
4629 : }
4630 :
4631 :
4632 0 : if (status == 0)
4633 : {
4634 :
4635 : /* Get origin order info */
4636 : /* --------------------- */
4637 0 : status = GDorigininfo(gridID, &origincode);
4638 0 : if (status < 0)
4639 0 : return -1;
4640 :
4641 :
4642 : /* Initialize start & edge arrays */
4643 : /* ------------------------------ */
4644 0 : for (i = 0; i < rank; i++)
4645 : {
4646 0 : start[i] = 0;
4647 0 : edge[i] = dims[i];
4648 : }
4649 :
4650 :
4651 : /* Compute size of data buffer for each pixel */
4652 : /* ------------------------------------------ */
4653 0 : edge[xdum] = 1;
4654 0 : edge[ydum] = 1;
4655 0 : size = edge[0];
4656 0 : for (j = 1; j < rank; j++)
4657 : {
4658 0 : size *= edge[j];
4659 : }
4660 0 : size *= DFKNTsize(ntype);
4661 :
4662 :
4663 :
4664 : /* If data values are requested ... */
4665 : /* -------------------------------- */
4666 0 : if (buffer != NULL)
4667 : {
4668 : /* get sdid */
4669 0 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname, &sdid,
4670 : &rankSDS, &rankFld, &mrgOffset, dims, &dum);
4671 :
4672 : /* Loop through all pixels */
4673 : /* ----------------------- */
4674 0 : for (i = 0; i < nPixels; i++)
4675 : {
4676 : /* Conmpute offset within returned data buffer */
4677 : /* ------------------------------------------- */
4678 0 : bufOffset = size * i;
4679 :
4680 :
4681 : /* If pixel row & column OK ... */
4682 : /* ---------------------------- */
4683 0 : if (pixCol[i] != -1 && pixRow[i] != -1)
4684 : {
4685 0 : start[xdum] = pixCol[i];
4686 0 : start[ydum] = pixRow[i];
4687 :
4688 :
4689 : /* Adjust X-dim start if origin on right edge */
4690 : /* ------------------------------------------ */
4691 0 : if ((origincode & 1) == 1)
4692 : {
4693 0 : start[xdum] = dims[xdum] - (start[xdum] + 1);
4694 : }
4695 :
4696 :
4697 : /* Adjust Y-dim start if origin on lower edge */
4698 : /* ------------------------------------------ */
4699 0 : if ((origincode & 2) == 2)
4700 : {
4701 0 : start[ydum] = dims[ydum] - (start[ydum] + 1);
4702 : }
4703 :
4704 : /* Set I/O offset and count Section */
4705 : /* ---------------------- */
4706 :
4707 : /*
4708 : * start and edge != NULL, set I/O offset and count to
4709 : * user values, adjusting the
4710 : * 0th field with the merged field offset (if any)
4711 : */
4712 0 : if (rankFld == rankSDS)
4713 : {
4714 0 : for (j = 0; j < rankSDS; j++)
4715 : {
4716 0 : offset[j] = start[j];
4717 0 : count[j] = edge[j];
4718 : }
4719 0 : offset[0] += mrgOffset;
4720 : }
4721 : else
4722 : {
4723 : /*
4724 : * If field really 2-dim merged in 3-dim field then set
4725 : * 0th field offset to merge offset and then next two to
4726 : * the user values
4727 : */
4728 0 : for (j = 0; j < rankFld; j++)
4729 : {
4730 0 : offset[j + 1] = start[j];
4731 0 : count[j + 1] = edge[j];
4732 : }
4733 0 : offset[0] = mrgOffset;
4734 0 : count[0] = 1;
4735 : }
4736 :
4737 :
4738 :
4739 : /* Set I/O stride Section */
4740 : /* ---------------------- */
4741 :
4742 : /* In original code stride entered as NULL.
4743 : Abe Taaheri June 12, 1998 */
4744 : /*
4745 : * If stride == NULL (default) set I/O stride to 1
4746 : */
4747 0 : for (j = 0; j < rankSDS; j++)
4748 : {
4749 0 : incr[j] = 1;
4750 : }
4751 :
4752 :
4753 : /* Read into data buffer */
4754 : /* --------------------- */
4755 0 : status = SDreaddata(sdid,
4756 : offset, incr, count,
4757 : (VOIDP) ((uint8 *) buffer + bufOffset));
4758 : }
4759 : }
4760 : }
4761 : }
4762 : }
4763 :
4764 :
4765 : /* If successful return size of returned data in bytes */
4766 : /* --------------------------------------------------- */
4767 0 : if (status == 0)
4768 : {
4769 0 : free(dimlist);
4770 0 : return (size * nPixels);
4771 : }
4772 : else
4773 : {
4774 0 : free(dimlist);
4775 0 : return ((int32) status);
4776 : }
4777 : }
4778 :
4779 : /***********************************************
4780 : GDwrrdtile --
4781 : This function is the underlying function below GDwritetile and
4782 : GDreadtile.
4783 :
4784 :
4785 : Author--
4786 : Alexis Zubrow
4787 :
4788 : ********************************************************/
4789 :
4790 : static intn
4791 0 : GDwrrdtile(int32 gridID, const char *fieldname, const char *code, int32 start[],
4792 : VOIDP datbuf)
4793 : {
4794 : intn i; /* Loop index */
4795 0 : intn status = 0; /* routine return status variable */
4796 :
4797 : int32 fid; /* HDF-EOS file ID */
4798 : int32 sdInterfaceID; /* HDF SDS interface ID */
4799 : int32 sdid; /* SDS ID */
4800 :
4801 : int32 dum; /* Dummy variable */
4802 : int32 rankSDS; /* Rank of SDS/Field */
4803 :
4804 : int32 dims[8]; /* Field/SDS dimensions */
4805 : int32 tileFlags; /* flag to determine if field is tiled */
4806 : int32 numTileDims;/* number of tiles spanning a dimension */
4807 : HDF_CHUNK_DEF tileDef; /* union holding tiling info. */
4808 :
4809 :
4810 : /* Get gridID */
4811 0 : status = GDchkgdid(gridID, "GDwrrdtile", &fid, &sdInterfaceID, &dum);
4812 0 : if (status == 0)
4813 : {
4814 :
4815 : /* Get field info */
4816 0 : status = GDfieldinfo(gridID, fieldname, &rankSDS, dims, &dum, NULL);
4817 :
4818 0 : if (status == 0)
4819 : {
4820 :
4821 : /* Check whether fieldname is in SDS (multi-dim field) */
4822 : /* --------------------------------------------------- */
4823 0 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname, &sdid,
4824 : &rankSDS, &dum, &dum, dims, &dum);
4825 0 : if (status < 0)
4826 0 : return -1;
4827 :
4828 :
4829 : /*
4830 : * Check for errors in parameters passed to GDwritetile or
4831 : * GDreadtile
4832 : */
4833 :
4834 : /* Check if untiled field */
4835 0 : status = SDgetchunkinfo(sdid, &tileDef, &tileFlags);
4836 0 : if (tileFlags == HDF_NONE)
4837 : {
4838 0 : HEpush(DFE_GENAPP, "GDwrrdtile", __FILE__, __LINE__);
4839 0 : HEreport("Field \"%s\" is not tiled.\n", fieldname);
4840 0 : status = -1;
4841 0 : return (status);
4842 :
4843 : }
4844 :
4845 : /*
4846 : * Check if rd/wr tilecoords are within the extent of the field
4847 : */
4848 0 : for (i = 0; i < rankSDS; i++)
4849 : {
4850 : /*
4851 : * Calculate the number of tiles which span a dimension of
4852 : * the field
4853 : */
4854 0 : numTileDims = dims[i] / tileDef.chunk_lengths[i];
4855 0 : if ((start[i] >= numTileDims) || (start[i] < 0))
4856 : {
4857 : /*
4858 : * ERROR INDICATING BEYOND EXTENT OF THAT DIMENSION OR
4859 : * NEGATIVE TILECOORDS
4860 : */
4861 0 : HEpush(DFE_GENAPP, "GDwrrdtile", __FILE__, __LINE__);
4862 0 : HEreport("Tilecoords for dimension \"%d\" ...\n", i);
4863 0 : HEreport("is beyond the extent of dimension length\n");
4864 0 : status = -1;
4865 :
4866 : }
4867 : }
4868 :
4869 0 : if (status == -1)
4870 : {
4871 0 : return (status);
4872 : }
4873 :
4874 :
4875 : /* Actually write/read to the field */
4876 :
4877 0 : if (strcmp(code, "w") == 0) /* write tile */
4878 : {
4879 0 : status = SDwritechunk(sdid, start, (VOIDP) datbuf);
4880 : }
4881 0 : else if (strcmp(code, "r") == 0) /* read tile */
4882 : {
4883 0 : status = SDreadchunk(sdid, start, (VOIDP) datbuf);
4884 : }
4885 :
4886 :
4887 : }
4888 :
4889 : /* Non-existent fieldname */
4890 : else
4891 : {
4892 0 : HEpush(DFE_GENAPP, "GDwrrdtile", __FILE__, __LINE__);
4893 0 : HEreport("Fieldname \"%s\" does not exist.\n", fieldname);
4894 0 : status = -1;
4895 : }
4896 :
4897 : }
4898 :
4899 0 : return (status);
4900 : }
4901 :
4902 : /***********************************************
4903 : GDtileinfo --
4904 : This function queries the field to determine if it is tiled. If it is
4905 : tile, one can retrieve some of the characteristics of the tiles.
4906 :
4907 : Author-- Alexis Zubrow
4908 :
4909 : ********************************************************/
4910 :
4911 :
4912 : intn
4913 1 : GDtileinfo(int32 gridID, const char *fieldname, int32 * tilecode, int32 * tilerank,
4914 : int32 tiledims[])
4915 :
4916 : {
4917 : intn i; /* Loop index */
4918 1 : intn status = 0; /* routine return status variable */
4919 :
4920 : int32 fid; /* HDF-EOS file ID */
4921 : int32 sdInterfaceID; /* HDF SDS interface ID */
4922 : int32 sdid; /* SDS ID */
4923 :
4924 : int32 dum; /* Dummy variable */
4925 : int32 rankSDS; /* Rank of SDS/Field/tile */
4926 :
4927 : int32 dims[8]; /* Field/SDS dimensions */
4928 : int32 tileFlags; /* flag to determine if field is tiled */
4929 : HDF_CHUNK_DEF tileDef; /* union holding tiling info. */
4930 :
4931 :
4932 : /* Check if improper gridID */
4933 1 : status = GDchkgdid(gridID, "GDtileinfo", &fid, &sdInterfaceID, &dum);
4934 1 : if (status == 0)
4935 : {
4936 :
4937 : /* Get field info */
4938 1 : status = GDfieldinfo(gridID, fieldname, &rankSDS, dims, &dum, NULL);
4939 :
4940 1 : if (status == 0)
4941 : {
4942 :
4943 : /* Check whether fieldname is in SDS (multi-dim field) */
4944 : /* --------------------------------------------------- */
4945 0 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname, &sdid,
4946 : &rankSDS, &dum, &dum, dims, &dum);
4947 0 : if (status < 0)
4948 0 : return -1;
4949 :
4950 : /* Query field for tiling information */
4951 0 : status = SDgetchunkinfo(sdid, &tileDef, &tileFlags);
4952 :
4953 : /* If field is untiled, return untiled flag */
4954 0 : if (tileFlags == HDF_NONE)
4955 : {
4956 0 : *tilecode = HDFE_NOTILE;
4957 0 : return (status);
4958 : }
4959 :
4960 : /* IF field is tiled or tiled with compression */
4961 0 : else if ((tileFlags == HDF_CHUNK) ||
4962 0 : (tileFlags == (HDF_CHUNK | HDF_COMP)))
4963 : {
4964 0 : if (tilecode != NULL)
4965 : {
4966 0 : *tilecode = HDFE_TILE;
4967 : }
4968 0 : if (tilerank != NULL)
4969 : {
4970 0 : *tilerank = rankSDS;
4971 : }
4972 0 : if (tiledims != NULL)
4973 : {
4974 : /* Assign size of tile dimensions */
4975 0 : for (i = 0; i < rankSDS; i++)
4976 : {
4977 0 : tiledims[i] = tileDef.chunk_lengths[i];
4978 : }
4979 : }
4980 : }
4981 : }
4982 :
4983 : /* Non-existent fieldname */
4984 : else
4985 : {
4986 1 : HEpush(DFE_GENAPP, "GDtileinfo", __FILE__, __LINE__);
4987 1 : HEreport("Fieldname \"%s\" does not exist.\n", fieldname);
4988 1 : status = -1;
4989 : }
4990 :
4991 : }
4992 1 : return (status);
4993 : }
4994 :
4995 : /***********************************************
4996 : GDreadtile --
4997 : This function reads one tile from a particular field.
4998 :
4999 :
5000 : Author--
5001 : Alexis Zubrow
5002 :
5003 : ********************************************************/
5004 :
5005 : intn
5006 0 : GDreadtile(int32 gridID, const char *fieldname, int32 tilecoords[],
5007 : VOIDP tileData)
5008 : {
5009 0 : char code[] = "r"; /* read tile code */
5010 0 : intn status = 0; /* routine return status variable */
5011 :
5012 0 : status = GDwrrdtile(gridID, fieldname, code, tilecoords, tileData);
5013 :
5014 0 : return (status);
5015 : }
5016 :
5017 : /*----------------------------------------------------------------------------|
5018 : | BEGIN_PROLOG |
5019 : | |
5020 : | FUNCTION: GDsdid |
5021 : | |
5022 : | DESCRIPTION: Returns SD element ID for grid field |
5023 : | |
5024 : | |
5025 : | Return Value Type Units Description |
5026 : | ============ ====== ========= ===================================== |
5027 : | status intn return status (0) SUCCEED, (-1) FAIL |
5028 : | |
5029 : | INPUTS: |
5030 : | gridID int32 grid structure ID |
5031 : | fieldname const char field name |
5032 : | |
5033 : | |
5034 : | OUTPUTS: |
5035 : | sdid int32 SD element ID |
5036 : | |
5037 : | NOTES: |
5038 : | |
5039 : | |
5040 : | Date Programmer Description |
5041 : | ====== ============ ================================================= |
5042 : | Oct 07 Andrey Kiselev Original Programmer |
5043 : | |
5044 : | END_PROLOG |
5045 : -----------------------------------------------------------------------------*/
5046 : intn
5047 6 : GDsdid(int32 gridID, const char *fieldname, int32 *sdid)
5048 : {
5049 : intn status; /* routine return status variable */
5050 : int32 fid; /* HDF-EOS file ID */
5051 : int32 sdInterfaceID; /* HDF SDS interface ID */
5052 : int32 dum; /* Dummy variable */
5053 : int32 dims[H4_MAX_VAR_DIMS]; /* Field/SDS dimensions */
5054 :
5055 6 : status = GDchkgdid(gridID, "GDsdid", &fid, &sdInterfaceID, &dum);
5056 6 : if (status != -1)
5057 : {
5058 6 : status = GDSDfldsrch(gridID, sdInterfaceID, fieldname,
5059 : sdid, &dum, &dum, &dum, dims, &dum);
5060 : }
5061 :
5062 6 : return (status);
5063 : }
|