1 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
2 * Copyright by The HDF Group. *
3 * Copyright by the Board of Trustees of the University of Illinois. *
4 * All rights reserved. *
5 * *
6 * This file is part of HDF. The full HDF copyright notice, including *
7 * terms governing use, modification, and redistribution, is contained in *
8 * the COPYING file, which can be found at the root of the source code *
9 * distribution tree, or in https://support.hdfgroup.org/ftp/HDF/releases/. *
10 * If you do not have access to either file, you may request a copy from *
11 * help@hdfgroup.org. *
12 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
13
14 /* $Id$ */
15
16 /*****************************************************************************
17 file - vio.c
18
19 Part of the HDF Vset interface.
20
21 VDATAs are handled by routines in here.
22 PRIVATE functions manipulate vsdir and are used only within this file.
23 PRIVATE data structures in here pertain to vdatas in vsdir only.
24
25
26 LOCAL ROUTINES
27 VSIget_vdata_node -- allocate a new VDATA record
28 VSIrelease_vdata_node -- Releases a vdata node
29 VSIget_vsinstance_node -- allocate a new vsinstance_t record
30 VSIrelease_vsinstance_node -- Releases a vsinstance node
31
32 LIBRARY PRIVATE ROUTINES
33 VSPhshutdown -- shutdown the Vset interface
34
35 EXPORTED ROUTINES
36 vinst -- Looks thru vstab for vsid and return the addr of the vdata
37 instance where vsid is found.
38 vexistvs -- Tests if a vdata with id vsid is in the file's vstab.
39 vpackvs -- Packs a VDATA structure into a compact form suitable for
40 storing in the HDF file.
41 vunpackvs -- Convert a packed form(from HDF file) to a VDATA structure.
42 This routine will also initalize the VDATA structure as
43 much as it can.
44 vsdestroynode -- Frees B-Tree nodes.
45 VSPgetinfo -- Read in the "header" information about the Vdata.
46 VSattach -- Attaches/Creates a new vs in vg depending on "vsid" value.
47 VSdetach -- Detaches vs from vstab.
48 VSappendable -- Make it possible to append unlimitedly to an existing VData.
49 VSgetid -- Returns the id of the next VDATA from the file.
50 VSQuerytag -- Return the 'otag' of the given Vdata.
51 VSQueryref -- Return the ref of the given Vdata.
52 vswritelist -- Return the writelist of a Vdata.
53 VSgetversion -- Return the version number of a Vdata.
54 VSdelete -- Remove a Vdata from its file. This function will both
55 remove the Vdata from the internal Vset data structures
56 as well as from the file.
57
58 NOTE: Another pass needs to made through this file to update some of
59 the comments about certain sections of the code. -GV 9/8/97
60
61 *************************************************************************/
62
63 #define VSET_INTERFACE
64 #include "hdf.h"
65
66 /* Private Function Prototypes */
67 PRIVATE intn vunpackvs
68 (VDATA * vs, uint8 buf[], int32 len);
69
70 /* Temporary buffer for I/O */
71 PRIVATE uint32 Vhbufsize = 0;
72 PRIVATE uint8 *Vhbuf = NULL;
73
74 /* Pointers to the VDATA & vsinstance node free lists */
75 static VDATA *vdata_free_list=NULL;
76 static vsinstance_t *vsinstance_free_list=NULL;
77
78 /* vpackvs is prototyped in vg.h since vconv.c needs to call it */
79
80 /*******************************************************************************
81 NAME
82 VSIget_vdata_node -- allocate a new VDATA record
83
84 DESCRIPTION
85 Return an pointer to a new VDATA to use for a new VSID.
86
87 RETURNS
88 returns VDATA record pointer or NULL if failed.
89
90 *******************************************************************************/
91 VDATA *
VSIget_vdata_node(void)92 VSIget_vdata_node(void)
93 {
94 VDATA *ret_value = NULL;
95 CONSTR(FUNC, "VSIget_vdata_node");
96
97 /* clear error stack */
98 HEclear();
99
100 /* Grab from free list if possible */
101 if(vdata_free_list != NULL)
102 {
103 ret_value = vdata_free_list;
104 vdata_free_list = vdata_free_list->next;
105 }
106 else /* allocate a new node */
107 {
108 if((ret_value=(VDATA *)HDmalloc(sizeof(VDATA)))==NULL)
109 HGOTO_ERROR(DFE_NOSPACE, NULL);
110 } /* end else */
111
112 /* Initialize to zeros */
113 HDmemset(ret_value,0,sizeof(VDATA));
114
115 done:
116 if(ret_value == NULL)
117 { /* Error condition cleanup */
118
119 } /* end if */
120
121 /* Normal function cleanup */
122
123 return(ret_value);
124 } /* VSIget_vdata_node */
125
126 /******************************************************************************
127 NAME
128 VSIrelease_vdata_node -- Releases a vdata node
129
130 DESCRIPTION
131 Puts an VDATA node into the free list
132
133 RETURNS
134 No return value
135
136 *******************************************************************************/
137 void
VSIrelease_vdata_node(VDATA * vs)138 VSIrelease_vdata_node(VDATA *vs /* IN: vdata to release */)
139 {
140 #ifdef LATER
141 CONSTR(FUNC, "VSIrelease_vdata_node"); /* for HERROR */
142 #endif /* LATER */
143
144 /* Insert the atom at the beginning of the free list */
145 vs->next = vdata_free_list;
146 vdata_free_list = vs;
147
148 } /* end VSIrelease_vdata_node() */
149
150 /*******************************************************************************
151 NAME
152 VSIget_vsinstance_node -- allocate a new vsinstance_t record
153
154 DESCRIPTION
155 Return an pointer to a new VDATA to use for a new VSID.
156
157 RETURNS
158 returns vsinstance_t pointer or NULL if failed.
159 *******************************************************************************/
160 vsinstance_t *
VSIget_vsinstance_node(void)161 VSIget_vsinstance_node(void)
162 {
163 vsinstance_t *ret_value = NULL;
164 CONSTR(FUNC, "VSIget_vsinstance_node");
165
166 /* clear error stack */
167 HEclear();
168
169 /* Grab from free list if possible */
170 if(vsinstance_free_list != NULL)
171 {
172 ret_value = vsinstance_free_list;
173 vsinstance_free_list = vsinstance_free_list->next;
174 }
175 else /* allocate a new vsinstance record */
176 {
177 if((ret_value=(vsinstance_t *)HDmalloc(sizeof(vsinstance_t)))==NULL)
178 HGOTO_ERROR(DFE_NOSPACE, NULL);
179 } /* end else */
180
181 /* Initialize to zeros */
182 HDmemset(ret_value,0,sizeof(vsinstance_t));
183
184 done:
185 if(ret_value == NULL)
186 { /* Error condition cleanup */
187
188 } /* end if */
189
190 /* Normal function cleanup */
191
192 return(ret_value);
193 } /* VSIget_vsinstance_node */
194
195 /******************************************************************************
196 NAME
197 VSIrelease_vsinstance_node -- Releases a vsinstance node
198
199 DESCRIPTION
200 Puts a vsinstance node into the free list
201
202 RETURNS
203 No return value
204
205 *******************************************************************************/
206 void
VSIrelease_vsinstance_node(vsinstance_t * vs)207 VSIrelease_vsinstance_node(vsinstance_t *vs /* IN: vinstance node to release */)
208 {
209 #ifdef LATER
210 CONSTR(FUNC, "VSIrelease_vsinstance_node"); /* for HERROR */
211 #endif /* LATER */
212
213 /* Insert the atom at the beginning of the free list */
214 vs->next = vsinstance_free_list;
215 vsinstance_free_list = vs;
216
217 } /* end VSIrelease_vsinstance_node() */
218
219 /*******************************************************************************
220 NAME
221 VSPhshutdown - shutdown the Vset interface
222
223 DESCRIPTION
224 For completeness, when the VSet interface is shut-down, free the Vhbuf.
225
226 RETURNS
227 Returns SUCCEED/FAIL
228
229 COMMENTS, BUGS, ASSUMPTIONS
230 Should only ever be called by the "atexit" function HDFend
231 *******************************************************************************/
232 intn
VSPhshutdown(void)233 VSPhshutdown(void)
234 {
235 intn ret_value = SUCCEED;
236 VDATA *v = NULL;
237 vsinstance_t *vs = NULL;
238
239 /* Release the vdata free-list if it exists */
240 if(vdata_free_list != NULL)
241 {
242 while(vdata_free_list != NULL)
243 {
244 v = vdata_free_list;
245 vdata_free_list = vdata_free_list->next;
246 v->next = NULL;
247 HDfree(v);
248 } /* end while */
249 } /* end if */
250
251 /* Release the vsinstance free-list if it exists */
252 if(vsinstance_free_list != NULL)
253 {
254 while(vsinstance_free_list != NULL)
255 {
256 vs = vsinstance_free_list;
257 vsinstance_free_list = vsinstance_free_list->next;
258 vs->next = NULL;
259 HDfree(vs);
260 } /* end while */
261 } /* end if */
262
263 /* free buffer */
264 if(Vhbuf != NULL)
265 {
266 HDfree(Vhbuf);
267 Vhbuf = NULL;
268 Vhbufsize = 0;
269 } /* end if */
270
271 /* free the parsing buffer */
272 ret_value = VPparse_shutdown();
273
274 return ret_value;
275 } /* end VSPhshutdown() */
276
277 /*******************************************************************************
278 NAME
279 vsint
280
281 DESCRIPTION
282 Looks thru vstab for vsid and return the addr of the vdata instance
283 where vsid is found.
284
285 RETURNS
286 RETURNS NULL if error or not found.
287 RETURNS vsinstance_t pointer if ok.
288
289 *******************************************************************************/
290 vsinstance_t *
vsinst(HFILEID f,uint16 vsid)291 vsinst(HFILEID f, /* IN: File handle */
292 uint16 vsid /* IN: vdata id i.e. ref */)
293 {
294 void * *t = NULL;
295 vfile_t *vf = NULL;
296 int32 key;
297 vsinstance_t *ret_value = NULL; /* FAIL */
298 CONSTR(FUNC, "vsinstance");
299
300 /* clear error stack */
301 HEclear();
302
303 /* Get Vdata file record? */
304 if (NULL == (vf = Get_vfile(f)))
305 HGOTO_ERROR(DFE_FNF, NULL);
306
307 /* tbbtdfind returns a pointer to the vsinstance_t pointer */
308 key = (int32)vsid;
309 if (( t = (void * *) tbbtdfind(vf->vstree, &key, NULL))== NULL)
310 HGOTO_ERROR(DFE_NOMATCH,NULL);
311
312 /* return the actual vsinstance_t ptr */
313 ret_value = ((vsinstance_t *) * t);
314
315 done:
316 if(ret_value == NULL)
317 { /* Error condition cleanup */
318
319 } /* end if */
320
321 /* Normal function cleanup */
322
323 return ret_value;
324 } /* vsinst */
325
326 /*******************************************************************************
327 NAME
328 vexistvs
329
330 DESCRIPTION
331 Tests if a vdata with id vsid is in the file's vstab.
332
333 RETURNS
334 returns FAIL if not found,
335 returns TRUE if found.
336 *******************************************************************************/
337 int32
vexistvs(HFILEID f,uint16 vsid)338 vexistvs(HFILEID f, /* IN: file handle */
339 uint16 vsid /* IN: vdata id i.e. ref */)
340 {
341 return ((NULL==vsinst(f, vsid)) ? FAIL : TRUE);
342 } /* vexistvs */
343
344 /* ------------------------------------------------------------------ */
345 /*
346 The following 2 routines, vpackvs and vunpackvs, packs and unpacks
347 a VDATA structure into a compact form suitable for storing in the HDF file.
348 */
349
350 /****
351 CONTENTS of VS stored in HDF file with tag VSDESCTAG:
352 int16 interlace
353 int32 nvertices
354 uint16 vsize
355 int16 nfields
356
357 uint16 isize[1..nfields] (internal size of each field)
358 uint16 off[1..nfields] (internal offset of each field)
359 char fname[1..nfields][FIELDNAMELENMAX]
360 char vsname[VSNAMELENMAX]
361 char vsclass[VSNAMELENMAX]
362 uint16 extag, exref
363 uint32 flags (for vset version 4 or higher )
364 int32 nattrs (if bit0 of flags is set)
365 uint16 atags[1..nattrs], arefs[1..nattrs]
366 int16 version, more
367 ****/
368
369 /* ------------------------------- vpackvs ----------------------------------- */
370 /*
371 The following 2 PRIVATE routines, vpackvs and vunpackvs, packs and unpacks
372 a VDATA structure into a compact form suitable for storing in the HDF file.
373 */
374
375 /****
376 CONTENTS of VS stored in HDF file with tag DFTAG_VH:
377 int16 interlace
378 int32 nvertices
379 uint16 vsize
380 int16 nfields
381
382 uint16 isize[1..nfields] (internal size of each field)
383 uint16 off[1..nfields] (internal offset of each field)
384 char fname[1..nfields][FIELDNAMELENMAX]
385 char vsname[VSNAMELENMAX]
386 char vsclass[VSNAMELENMAX]
387
388 ****/
389
390 /*******************************************************************************
391 NAME
392 vpackvs
393
394 DESCRIPTION
395 convert a vs struct to a vspack suitable for storage in a HDF file
396
397 RETURNS
398 always SUCCEED?
399
400 *******************************************************************************/
401 intn
vpackvs(VDATA * vs,uint8 buf[],int32 * size)402 vpackvs(VDATA * vs, /* IN/OUT: */
403 uint8 buf[], /* IN: */
404 int32 *size /* OUT: */)
405 {
406 #ifdef LATER
407 CONSTR(FUNC, "vpackvg");
408 #endif /* LATER */
409
410 int32 i;
411 int16 slen;
412 uint8 *bb = NULL;
413 intn ret_value = SUCCEED;
414
415 /* clear error stack */
416 HEclear();
417
418 bb = &buf[0];
419
420 /* save the interlace */
421 INT16ENCODE(bb, vs->interlace);
422
423 /* save nvertices */
424 INT32ENCODE(bb, vs->nvertices);
425
426 /* save ivsize */
427 UINT16ENCODE(bb, vs->wlist.ivsize);
428
429 /* save nfields */
430 INT16ENCODE(bb, vs->wlist.n);
431
432 /* Skip over all the "wheel-spinning" for 0-field vdatas */
433 if(vs->wlist.n>0)
434 {
435 for (i = 0; i < vs->wlist.n; i++) /* save the type */
436 INT16ENCODE(bb, vs->wlist.type[i]);
437
438 /* save the isize */
439 for (i = 0; i < vs->wlist.n; i++)
440 UINT16ENCODE(bb, vs->wlist.isize[i]);
441
442 for (i = 0; i < vs->wlist.n; i++) /* save the offset */
443 UINT16ENCODE(bb, vs->wlist.off[i]);
444
445 for (i = 0; i < vs->wlist.n; i++) /* save the order */
446 UINT16ENCODE(bb, vs->wlist.order[i]);
447
448 /* save each field length and name - omit the null */
449 for (i = 0; i < vs->wlist.n; i++)
450 {
451 slen = HDstrlen(vs->wlist.name[i]);
452 INT16ENCODE(bb, slen);
453
454 HDstrcpy((char *) bb, vs->wlist.name[i]);
455 bb += slen;
456 }
457 } /* end if */
458
459 /* save the vsnamelen and vsname - omit the null */
460 slen = HDstrlen(vs->vsname);
461 INT16ENCODE(bb, slen);
462
463 HDstrcpy((char *) bb, vs->vsname);
464 bb += slen;
465
466 /* save the vsclasslen and vsclass- omit the null */
467 slen = HDstrlen(vs->vsclass);
468 INT16ENCODE(bb, slen);
469
470 HDstrcpy((char *) bb, vs->vsclass);
471 bb += slen;
472
473 /* save the expansion tag/ref pair */
474 UINT16ENCODE(bb, vs->extag);
475 UINT16ENCODE(bb, vs->exref);
476
477 /* save the version field - to version_3 now if no new feature */
478 INT16ENCODE(bb, vs->version);
479
480 /* save the 'more' field - NONE now */
481 INT16ENCODE(bb, vs->more);
482
483 if (vs->flags != 0)
484 { /* save the flags and update version # */
485 UINT32ENCODE(bb, vs->flags);
486
487 if (vs->flags & VS_ATTR_SET)
488 { /* save attributes */
489 INT32ENCODE(bb, vs->nattrs);
490
491 for (i = 0; i < vs->nattrs; i++)
492 {
493 INT32ENCODE(bb, vs->alist[i].findex);
494 UINT16ENCODE(bb, vs->alist[i].atag);
495 UINT16ENCODE(bb, vs->alist[i].aref);
496 } /* for */
497 } /* attr set */
498 } /* flags set */
499
500 /* duplicate 'version' and 'more' - for new version of libraries */
501 /* see the documentation in vattr.c */
502 INT16ENCODE(bb, vs->version);
503
504 /* save the 'more' field - NONE now */
505 INT16ENCODE(bb, vs->more);
506
507 *size = (int32) (bb - buf) + 1;
508 *bb = 0;
509
510 #ifdef LATER
511 done:
512 if (ret_value == FAIL)
513 { /* Error condition cleanup */
514
515 } /* end if */
516 #endif /* LATER */
517
518 /* Normal function cleanup */
519 return ret_value;
520 } /* vpackvs */
521
522 /*******************************************************************************
523 NAME
524 vunpackvs
525
526 DESCRIPTION
527 Convert a packed form(from HDF file) to a VDATA structure.
528 This routine will also initalize the VDATA structure as much as it can.
529
530 RETURNS
531 SUCCEED / FAIL
532
533 *******************************************************************************/
534 PRIVATE intn
vunpackvs(VDATA * vs,uint8 buf[],int32 len)535 vunpackvs(VDATA * vs, /* IN/OUT: */
536 uint8 buf[],/* IN: */
537 int32 len /* IN: */)
538 {
539 uint8 *bb = NULL;
540 int32 i;
541 int16 int16var, temp;
542 uint16 uint16var;
543 int32 ret_value = SUCCEED;
544 CONSTR(FUNC, "vunpackvs");
545
546 /* clear error stack */
547 HEclear();
548
549 /* '5' is a magic number, the exact amount of space for 2 uint16's */
550 /* the magic number _should_ be '4', but the size of the Vdata */
551 /* information is incorrectly calculated (in vpackvs() above) when the */
552 /* info is written to the file and it's too late to change it now :- ( */
553 /* get version number first -- this is different from version 3
554 vdata interface */
555 bb = &buf[len - 5];
556 UINT16DECODE(bb, uint16var); /* retrieve the vg's version field */
557
558 vs->version = (int16)uint16var;
559 UINT16DECODE(bb, uint16var); /* retrieve the vg's more field */
560
561 vs->more = (int16)uint16var;
562 bb = &buf[0];
563
564 if (vs->version <= 4)
565 {
566 /* retrieve interlace */
567 INT16DECODE(bb, vs->interlace);
568
569 /* retrieve nvertices */
570 INT32DECODE(bb, vs->nvertices);
571
572 /* retrieve tore ivsize */
573 UINT16DECODE(bb, vs->wlist.ivsize);
574
575 /* retrieve nfields */
576 INT16DECODE(bb, int16var);
577 vs->wlist.n = (intn)int16var;
578
579 if(vs->wlist.n==0)
580 { /* Special case for Vdata with 0 fields defined */
581 /* Initialize buffer to NULL & carry over to other arrays */
582 vs->wlist.bptr = NULL;
583 vs->wlist.type = NULL;
584 vs->wlist.off = NULL;
585 vs->wlist.isize = NULL;
586 vs->wlist.order = NULL;
587 vs->wlist.esize = NULL;
588
589 /* Initialize the array of pointers to field names to NULL also */
590 vs->wlist.name = NULL;
591 } /* end if */
592 else
593 { /* Allocate buffer to hold all the int16/uint16 arrays */
594 if(NULL==(vs->wlist.bptr = HDmalloc(sizeof(uint16)*(size_t)(vs->wlist.n*5))))
595 HGOTO_ERROR(DFE_NOSPACE, FAIL);
596
597 /* Use buffer to support the other arrays */
598 vs->wlist.type = (int16 *)vs->wlist.bptr;
599 vs->wlist.off = (uint16 *)vs->wlist.type+vs->wlist.n;
600 vs->wlist.isize = vs->wlist.off+vs->wlist.n;
601 vs->wlist.order = vs->wlist.isize+vs->wlist.n;
602 vs->wlist.esize = vs->wlist.order+vs->wlist.n;
603
604 for (i = 0; i < vs->wlist.n; i++) /* retrieve the type */
605 INT16DECODE(bb, vs->wlist.type[i]);
606
607 for (i = 0; i < vs->wlist.n; i++) /* retrieve the isize */
608 UINT16DECODE(bb, vs->wlist.isize[i]);
609
610 for (i = 0; i < vs->wlist.n; i++) /* retrieve the offset */
611 UINT16DECODE(bb, vs->wlist.off[i]);
612
613 for (i = 0; i < vs->wlist.n; i++) /* retrieve the order */
614 UINT16DECODE(bb, vs->wlist.order[i]);
615
616 /* retrieve the field names (and each field name's length) */
617 if(NULL==(vs->wlist.name = HDmalloc(sizeof(char *)*(size_t)vs->wlist.n)))
618 HGOTO_ERROR(DFE_NOSPACE, FAIL);
619
620 for (i = 0; i < vs->wlist.n; i++)
621 {
622 INT16DECODE(bb, int16var); /* this gives the length */
623 if(NULL==(vs->wlist.name[i] = HDmalloc((int16var+1)*sizeof(char))))
624 HGOTO_ERROR(DFE_NOSPACE, FAIL);
625
626 HIstrncpy(vs->wlist.name[i], (char *) bb, int16var + 1);
627
628 bb += (size_t)int16var;
629 }
630 } /* end else */
631
632 /* retrieve the vsname (and vsnamelen) */
633 INT16DECODE(bb, int16var); /* this gives the length */
634
635 HIstrncpy(vs->vsname, (char *) bb, int16var + 1);
636 bb += (size_t)int16var;
637
638 /* retrieve the vsclass (and vsclasslen) */
639 INT16DECODE(bb, int16var); /* this gives the length */
640
641 HIstrncpy(vs->vsclass, (char *) bb, int16var + 1);
642 bb += (size_t)int16var;
643
644 /* retrieve the expansion tag and ref */
645 UINT16DECODE(bb, vs->extag);
646 UINT16DECODE(bb, vs->exref);
647
648 /* retrieve the middle version field */
649 INT16DECODE(bb, temp);
650 if (temp != vs->version)
651 HGOTO_ERROR(DFE_BADVH, FAIL);
652
653 /* retrieve the 'more' field */
654 INT16DECODE(bb, temp);
655 if (temp != vs->more)
656 HGOTO_ERROR(DFE_BADVH, FAIL);
657
658 if (vs->version == VSET_NEW_VERSION)
659 { /* new features exist */
660 UINT32DECODE(bb, vs->flags);
661 if (vs->flags & VS_ATTR_SET)
662 { /* get attr info */
663 INT32DECODE(bb, vs->nattrs);
664
665 if (NULL == (vs->alist = (vs_attr_t *)HDmalloc(vs->nattrs*sizeof(vs_attr_t))))
666 HGOTO_ERROR(DFE_NOSPACE, FAIL);
667
668 for (i=0; i<vs->nattrs; i++)
669 {
670 INT32DECODE(bb, vs->alist[i].findex);
671 UINT16DECODE(bb, vs->alist[i].atag);
672 UINT16DECODE(bb, vs->alist[i].aref);
673 } /* for */
674 } /* attr set */
675 } /* new version */
676
677 if (vs->version <= VSET_OLD_TYPES)
678 {
679 for (i = 0; i < vs->wlist.n; i++) /* save the type */
680 vs->wlist.type[i] = map_from_old_types((intn)vs->wlist.type[i]);
681 }
682
683 /* --- EXTRA --- fill in the machine-dependent size fields */
684 for (i = 0; i < vs->wlist.n; i++)
685 {
686 vs->wlist.esize[i] = (uint16) (vs->wlist.order[i] *
687 DFKNTsize((int32) vs->wlist.type[i] | (int32) DFNT_NATIVE));
688 }
689 } /* if version <= 4 */
690
691 done:
692 if (ret_value == FAIL)
693 { /* Error condition cleanup */
694
695 } /* end if */
696
697 /* Normal function cleanup */
698 return ret_value;
699 } /* vunpackvs */
700
701 /*******************************************************************************
702 NAME
703 vsdestroynode
704
705 DESCRIPTION
706 Frees B-Tree nodes
707
708 *** Only called by B-tree routines, should _not_ be called externally ***
709 *** unless you know what your are doing ***
710
711 RETURNS
712 Nothing
713
714 *******************************************************************************/
715 void
vsdestroynode(void * n)716 vsdestroynode(void * n /* IN: Node in TBBT-tree */)
717 {
718 VDATA *vs = NULL;
719 intn i;
720
721 if (n != NULL)
722 {
723 vs = ((vsinstance_t *) n)->vs;
724 if (vs != NULL)
725 {
726 /* Free the dynamicly allocated VData fields */
727 for(i=0; i<vs->wlist.n; i++)
728 HDfree(vs->wlist.name[i]);
729
730 HDfree(vs->wlist.name);
731 HDfree(vs->wlist.bptr);
732
733 if(vs->rlist.item != NULL)
734 HDfree(vs->rlist.item);
735
736 if (vs->alist != NULL)
737 HDfree(vs->alist);
738
739 VSIrelease_vdata_node(vs);
740 } /* end if */
741
742 /* relase this instance to the free list ? */
743 VSIrelease_vsinstance_node((vsinstance_t *)n);
744 } /* end if 'n' */
745
746 } /* vsdestroynode */
747
748 /*******************************************************************************
749 NAME
750 VSPgetinfo -- Read in the "header" information about the Vdata.
751
752 DESCRIPTION
753 This routine pre-reads the header information for a Vdata into memory
754 so that it can be accessed more quickly by the routines that need it.
755
756 RETURNS
757 Return a pointer to a VDATA filled with the Vdata information on success,
758 NULL on failure.
759
760 *******************************************************************************/
761 VDATA *
VSPgetinfo(HFILEID f,uint16 ref)762 VSPgetinfo(HFILEID f, /* IN: file handle */
763 uint16 ref /* IN: ref of the Vdata */)
764 {
765 VDATA *vs = NULL; /* new vdata to be returned */
766 /* int32 vh_length; int32 is mismatches Vhbuf's type -- uint32 */
767 size_t vh_length; /* length of the vdata header */
768 VDATA *ret_value = NULL; /* FAIL */
769 CONSTR(FUNC, "VSPgetinfo");
770
771 /* clear error stack */
772 HEclear();
773
774 /* get a free Vdata node? */
775 if ((vs = VSIget_vdata_node()) == NULL)
776 HGOTO_ERROR(DFE_NOSPACE, NULL);
777
778 /* need to fetch length of vdata from file */
779 if ((vh_length = Hlength(f,DFTAG_VH,ref)) == FAIL)
780 HGOTO_ERROR(DFE_BADLEN, NULL);
781
782 if(vh_length > Vhbufsize)
783 {
784 Vhbufsize = vh_length;
785
786 if (Vhbuf != NULL)
787 HDfree(Vhbuf);
788
789 if ((Vhbuf = (uint8 *) HDmalloc(Vhbufsize)) == NULL)
790 HGOTO_ERROR(DFE_NOSPACE, NULL);
791 } /* end if */
792
793 /* get Vdata header from file */
794 if (Hgetelement(f,DFTAG_VH,ref,Vhbuf) == FAIL)
795 HGOTO_ERROR(DFE_NOVS, NULL);
796
797 /* init all other fields in vdata
798 and then unpack the vdata */
799 vs->otag = DFTAG_VH;
800 vs->oref = ref;
801 vs->f = f;
802 if (FAIL == vunpackvs (vs,Vhbuf, vh_length))
803 HGOTO_ERROR(DFE_INTERNAL, NULL);
804
805 /* return vdata */
806 ret_value = (vs);
807
808 done:
809 if(ret_value == NULL)
810 { /* Error condition cleanup */
811
812 } /* end if */
813
814 /* Normal function cleanup */
815
816 return ret_value;
817 } /* end VSPgetinfo() */
818
819
820 /*******************************************************************************
821 NAME
822 VSattach
823
824 DESCRIPTION
825 NEW VSattach:
826 (a) if vsid == -1
827 if "r" access return error.
828 if "w" access
829 create a new vs in vg and attach it.
830 add to vsdir, set nattach= 1, nvertices = 0.
831
832 (b) if (vsid > 0)
833 if "r" access => look in vsdir
834 if not found,
835 fetch vs from file, add to vsdir,
836 set nattach= 1, nvertices = val from file.
837 if found,
838 check access of found vs
839 if "w" => being written, unstable! forbidden
840 if "r" => ok. incr nattach.
841
842 if "w" access => new data may be added BUT must be same format
843 as existing vdata.
844 (ie. VSsetfields must match old format exactly!!)
845
846 Allows for seeks to write.
847
848 in all cases, set the marked flag to 0.
849 returns NULL if error.
850
851 OLD VSattach:
852 if vsid == -1, then
853 (a) if vg is "w", create a new vs in vg and attach it.
854 add to vsdir, set nattach= 1, nvertices = 0.
855 (b) if vg is "r", forbidden.
856 if vsid is +ve, then
857 (a) if vg is "w" => new data may be added BUT must be same format
858 as existing vdata.
859 (ie. VSsetfields must match old format exactly!!)
860
861 (b) if vg is "r" => look in vsdir
862 if not found,
863 fetch vs from file, add to vsdir,
864 set nattach= 1, nvertices = val from file.
865 if found,
866 check access of found vs
867 if "w" => being written, unstable! forbidden
868 if "r" => ok. incr nattach.
869
870 in all cases, set the marked flag to 0.
871 returns NULL if error.
872
873 RETURNS
874
875
876 *******************************************************************************/
877 int32
VSattach(HFILEID f,int32 vsid,const char * accesstype)878 VSattach(HFILEID f, /* IN: file handle */
879 int32 vsid, /* IN: vdata id i.e. ref */
880 const char *accesstype /* IN: access type */)
881 {
882 VDATA *vs = NULL; /* new vdata to be returned */
883 vsinstance_t *w = NULL;
884 vfile_t *vf = NULL;
885 int32 acc_mode;
886 int32 ret_value = FAIL;
887 CONSTR(FUNC, "VSattach");
888
889 /* clear error stack */
890 HEclear();
891
892 /* check file and vdata handles */
893 if ((f == FAIL) || (vsid < -1))
894 HGOTO_ERROR(DFE_ARGS, FAIL);
895
896 /* get vdata file record */
897 if (NULL == (vf = Get_vfile(f)))
898 HGOTO_ERROR(DFE_FNF, FAIL);
899
900 /* check access type and covert to internal mode? */
901 if (accesstype[0] == 'R' || accesstype[0] == 'r')
902 acc_mode = 'r';
903 else if (accesstype[0] == 'W' || accesstype[0] == 'w')
904 acc_mode = 'w';
905 else
906 HGOTO_ERROR(DFE_BADACC, FAIL);
907
908 /* */
909 if (vsid == -1)
910 { /* ---------- VSID IS -1 -----------------------
911 if "r" access return error.
912 if "w" access
913 create a new vs in vg and attach it.
914 add to vsdir, set nattach= 1, nvertices = 0.
915 */
916 if (acc_mode == 'r')
917 HGOTO_ERROR(DFE_BADACC, FAIL);
918
919 /* otherwise 'w' */
920 /* allocate space for vs, & zero it out */
921 if ((vs = VSIget_vdata_node()) == NULL)
922 HGOTO_ERROR(DFE_NOSPACE, FAIL);
923
924 vs->otag = DFTAG_VH;
925 vs->oref = Hnewref(f);
926 if (vs->oref == 0)
927 {
928 VSIrelease_vdata_node(vs);
929 HGOTO_ERROR(DFE_NOREF, FAIL);
930 }
931
932 vs->interlace = FULL_INTERLACE; /* DEFAULT */
933 vs->access = 'w';
934 vs->f = f;
935 vs->version = VSET_VERSION;
936
937 /* attach new vs to file's vstab */
938 if (NULL == (w = VSIget_vsinstance_node()))
939 HGOTO_ERROR(DFE_NOSPACE, FAIL);
940
941 vf->vstabn++;
942 w->key = (int32) vs->oref; /* set the key for the node */
943 w->ref = (uintn) vs->oref;
944 w->vs = vs;
945 w->nattach = 1;
946 w->nvertices = 0;
947
948 /* insert the vs instance in B-tree */
949 tbbtdins(vf->vstree, w, NULL);
950
951 vs->instance = w;
952 } /* end of case where vsid is -1 */
953 else
954 { /* -------- VSID IS NON_NEGATIVE -------------
955 if "r" access => look in vsdir
956 if not found,
957 fetch vs from file, add to vsdir,
958 set nattach= 1, nvertices = val from file.
959 if found,
960 check access of found vs
961 if "w" => being written, unstable! forbidden
962 if "r" => ok. incr nattach.
963
964 if "w" access => new data may be added BUT must be same format
965 as existing vdata.
966 (ie. VSsetfields must match old format exactly!!)
967
968 Allows for seeks to write.
969
970 in all cases, set the marked flag to 0.
971 returns NULL if error.
972 */
973
974 if (NULL == (w = vsinst(f, (uint16) vsid)))
975 HGOTO_ERROR(DFE_VTAB, FAIL);
976
977 if (acc_mode == 'r')
978 { /* reading an existing vdata */
979 /* this vdata is already attached for 'r', ok to do so again */
980 /* then reset the read position to the beginning of the vdata */
981 if (w->nattach && w->vs->access == 'r')
982 {
983 accrec_t *access_rec; /* access record */
984
985 w->nattach++;
986
987 /* get the access_rec pointer to reset position */
988 if ((access_rec = HAatom_object(w->vs->aid)) == NULL)
989 HGOTO_ERROR(DFE_ARGS, FAIL);
990 access_rec->posn = 0; /* to fix bugzilla #486 - BMR, Dec, 05 */
991 }
992 else
993 {
994 vs = w->vs;
995
996 vs->access = 'r';
997 vs->aid = Hstartread(vs->f, VSDATATAG, vs->oref);
998 if (vs->aid == FAIL)
999 HGOTO_ERROR(DFE_BADAID, FAIL);
1000
1001 vs->instance = w;
1002
1003 /* attach vs to vsdir at the vdata instance w */
1004 w->nattach = 1;
1005 w->nvertices = vs->nvertices;
1006 } /* end else */
1007 } /* end of case where vsid is positive, and "r" */
1008 else
1009 { /* writing to an existing vdata */
1010 if (w->nattach) /* vdata previously attached before */
1011 HGOTO_ERROR(DFE_BADATTACH, FAIL);
1012
1013 vs = w->vs;
1014
1015 vs->access = 'w';
1016 vs->aid = Hstartwrite(vs->f, VSDATATAG, vs->oref, 0);
1017 if (vs->aid == FAIL)
1018 HGOTO_ERROR(DFE_BADAID, FAIL);
1019
1020 vs->instance = w;
1021 vs->new_h_sz = 0;
1022
1023 /* attach vs to vsdir at the vdata instance w */
1024 w->nattach = 1;
1025 w->nvertices = vs->nvertices;
1026 } /* end of case where vsid is positive, and "w" */
1027 } /* end else */
1028
1029 /* register this vdata with group */
1030 ret_value = HAregister_atom(VSIDGROUP,w);
1031
1032 /* Make VDatas appendable by default */
1033 if (FAIL == VSappendable(ret_value,VDEFAULTBLKSIZE))
1034 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1035
1036 done:
1037 if(ret_value == FAIL)
1038 { /* Error condition cleanup */
1039
1040 } /* end if */
1041
1042 /* Normal function cleanup */
1043
1044 return ret_value;
1045 } /* VSattach */
1046
1047 /*******************************************************************************
1048 NAME
1049 VSdetach
1050
1051 DESCRIPTION
1052 Detach vs from vstab.
1053
1054 if vs has "w" access, ( <=> only attached ONCE! )
1055 decr nattach.
1056 if (nattach is not 0) => bad error in code.
1057 if nvertices (in vs) is 0) just free vs from vstab.
1058
1059 if marked flag is 1
1060 write out vs to file and set marked flag to 0.
1061 free vs from vsdir.
1062
1063 if vs has "r" access, ( <=> only attached ONCE! )
1064 decr nattach.
1065 if (nattach is 0) just free vs from vstab.
1066
1067 RETURNS
1068 SUCCEED / FAIL
1069
1070 *******************************************************************************/
1071 int32
VSdetach(int32 vkey)1072 VSdetach(int32 vkey /* IN: vdata key? */)
1073 {
1074 int32 i;
1075 int32 ret;
1076 int32 vspacksize;
1077 vsinstance_t *w = NULL;
1078 VDATA *vs = NULL;
1079 int32 ret_value = SUCCEED;
1080 CONSTR(FUNC, "VSdetach");
1081
1082 /* clear error stack */
1083 HEclear();
1084
1085 /* check if vdata is part of vdata group */
1086 if (HAatom_group(vkey) != VSIDGROUP)
1087 HGOTO_ERROR(DFE_ARGS, FAIL);
1088
1089 /* get vdata instance */
1090 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1091 HGOTO_ERROR(DFE_NOVS, FAIL);
1092
1093 /* get vdata itself and check it */
1094 vs = w->vs;
1095 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1096 HGOTO_ERROR(DFE_ARGS,FAIL);
1097
1098 w->nattach--; /* detach from vdata */
1099
1100 /* --- case where access was 'r' --- */
1101 if (vs->access == 'r')
1102 {
1103 if (w->nattach == 0)
1104 { /* end access to vdata */
1105 if (Hendaccess(vs->aid) == FAIL)
1106 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1107 vs->aid = FAIL;
1108
1109 /* remove from atom list */
1110 if(HAremove_atom(vkey)==NULL)
1111 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1112 } /* end if */
1113
1114 /* we are done */
1115 HGOTO_DONE(SUCCEED);
1116 }
1117 else /* must be write */
1118 {
1119 /* --- case where access was 'w' --- */
1120 if (w->nattach != 0)
1121 HGOTO_ERROR(DFE_CANTDETACH, FAIL);
1122
1123 if (vs->marked)
1124 { /* if marked , write out vdata's VSDESC to file */
1125 size_t need;
1126
1127 need = sizeof(VWRITELIST) +
1128 (size_t)vs->nattrs*sizeof(vs_attr_t) + sizeof(VDATA) + 1;
1129
1130 if(need > Vhbufsize)
1131 {
1132 Vhbufsize = need;
1133 if (Vhbuf)
1134 HDfree(Vhbuf);
1135
1136 if ((Vhbuf = HDmalloc(Vhbufsize)) == NULL)
1137 HGOTO_ERROR(DFE_NOSPACE, FAIL);
1138 } /* end if */
1139
1140 if (FAIL == vpackvs(vs, Vhbuf, &vspacksize))
1141 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1142
1143 /* if VH size changed we need to re-use the tag/ref
1144 * for new header. This will cause the pointer to the
1145 * original vdata header to be lost but this is okay. */
1146 if (vs->new_h_sz)
1147 {
1148 /* check if tag/ref exists in DD list already */
1149 switch(HDcheck_tagref(vs->f, DFTAG_VH, vs->oref))
1150 {
1151 case 0: /* not found */
1152 break;
1153 case 1: /* found, reuse tag/ref */
1154 if (HDreuse_tagref(vs->f, DFTAG_VH, vs->oref) == FAIL)
1155 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1156 break;
1157 case -1: /* error */
1158 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1159 default: /* should never get here */
1160 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1161 }
1162 }
1163
1164 /* write new one */
1165 ret = Hputelement(vs->f, VSDESCTAG, vs->oref, Vhbuf, vspacksize);
1166 if (ret == FAIL)
1167 HGOTO_ERROR(DFE_WRITEERROR, FAIL);
1168
1169 vs->marked = 0;
1170 vs->new_h_sz = 0;
1171 }
1172
1173 /* remove all defined symbols */
1174 for (i = 0; i < vs->nusym; i++)
1175 HDfree(vs->usym[i].name);
1176
1177 if(vs->usym!=NULL)
1178 HDfree(vs->usym); /* free the actual array */
1179
1180 vs->nusym = 0;
1181 vs->usym=NULL;
1182
1183 /* end access to vdata */
1184 if (Hendaccess(vs->aid) == FAIL)
1185 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1186 vs->aid = FAIL;
1187
1188 /* remove vdata from atom list */
1189 if(HAremove_atom(vkey)==NULL)
1190 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1191
1192 } /* end of 'write' case */
1193
1194 done:
1195 if(ret_value == FAIL)
1196 { /* Error condition cleanup */
1197
1198 } /* end if */
1199
1200 /* Normal function cleanup */
1201 return ret_value;
1202 } /* VSdetach */
1203
1204 /*******************************************************************************
1205 NAME
1206 VSappendable
1207
1208 DESCRIPTION
1209 Make it possible to append unlimitedly to an existing VData
1210
1211 RETURNS
1212 SUCCEED, or FAIL for error
1213 *******************************************************************************/
1214 int32
VSappendable(int32 vkey,int32 blk)1215 VSappendable(int32 vkey, /* IN: vdata key */
1216 int32 blk /* IN: */)
1217 {
1218 vsinstance_t *w = NULL;
1219 VDATA *vs = NULL;
1220 int32 ret_value = SUCCEED;
1221 CONSTR(FUNC, "VSappendable");
1222
1223 /* clear error stack */
1224 HEclear();
1225
1226 /* shut compiler up */
1227 blk = blk;
1228
1229 /* check vdata key is a valid */
1230 if (HAatom_group(vkey) != VSIDGROUP)
1231 HGOTO_ERROR(DFE_ARGS, FAIL);
1232
1233 /* get vdata instance */
1234 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1235 HGOTO_ERROR(DFE_NOVS, FAIL);
1236
1237 /* get Vdata itself and check */
1238 vs = w->vs;
1239 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1240 HGOTO_ERROR(DFE_ARGS, FAIL);
1241
1242 if(vs->aid == 0)
1243 vs->aid = Hstartaccess(vs->f, VSDATATAG, vs->oref, DFACC_RDWR|DFACC_APPENDABLE);
1244 else
1245 ret_value = Happendable(vs->aid);
1246
1247 done:
1248 if(ret_value == FAIL)
1249 { /* Error condition cleanup */
1250
1251 } /* end if */
1252
1253 /* Normal function cleanup */
1254 return ret_value;
1255 } /* VSappendable */
1256
1257 /*******************************************************************************
1258 NAME
1259 VSgetid
1260
1261 DESCRIPTION
1262 returns the id of the next VDATA from the file f .
1263 (vsid = -1 gets the 1st vDATA).
1264
1265 RETURNS
1266 RETURNS -1 on error.
1267 RETURNS vdata id (0 or +ve integer)
1268
1269 *******************************************************************************/
1270 int32
VSgetid(HFILEID f,int32 vsid)1271 VSgetid(HFILEID f, /* IN: file handle */
1272 int32 vsid /* IN: vdata id i.e. ref */)
1273 {
1274 vsinstance_t *w = NULL;
1275 vfile_t *vf = NULL;
1276 void * *t = NULL;
1277 int32 key;
1278 int32 ret_value = SUCCEED;
1279 CONSTR(FUNC, "VSgetid");
1280
1281 /* clear error stack */
1282 HEclear();
1283
1284 /* check valid vdata id */
1285 if (vsid < -1)
1286 HGOTO_ERROR(DFE_ARGS, FAIL);
1287
1288 /* get vdata file record */
1289 if (NULL == (vf = Get_vfile(f)))
1290 HGOTO_ERROR(DFE_FNF, FAIL);
1291
1292 if (vsid == -1)
1293 { /* vsid '-1' case */
1294
1295 if (vf->vstree==NULL)
1296 HGOTO_DONE(FAIL);
1297
1298 if ((t = (void **)tbbtfirst((TBBT_NODE *) * (vf->vstree))) == NULL)
1299 HGOTO_DONE(FAIL);
1300
1301 /* we assume 't' is valid at this point */
1302 w = (vsinstance_t *) * t; /* get actual pointer to the vsinstance_t */
1303 HGOTO_DONE((int32)w->ref);/* rets 1st vdata's ref */
1304 }
1305 else /* vsid >= 0 */
1306 {
1307 /* tbbtdfind returns a pointer to the vsinstance_t pointer */
1308 key = (int32)vsid;
1309 t = (void * *) tbbtdfind(vf->vstree, &key, NULL);
1310
1311 if (t == NULL) /* couldn't find the old vsid */
1312 ret_value = (FAIL);
1313 else if (NULL == (t = (void * *) tbbtnext((TBBT_NODE *) t))) /* get the next node in the tree */
1314 ret_value = (FAIL);
1315 else
1316 {
1317 w = (vsinstance_t *) * t; /* get actual pointer to the vsinstance_t */
1318 ret_value = (int32)w->ref; /* rets vdata's ref */
1319 } /* end else */
1320 }
1321
1322 done:
1323 if(ret_value == FAIL)
1324 { /* Error condition cleanup */
1325
1326 } /* end if */
1327
1328 /* Normal function cleanup */
1329 return ret_value;
1330 } /* VSgetid */
1331
1332 /*******************************************************************************
1333 NAME
1334 VSQuerytag
1335
1336 DESCRIPTION
1337 get the 'otag' of the given Vdata
1338
1339 RETURNS
1340 Return the 'otag' of the given Vdata
1341 Return FAIL on failure
1342
1343 *******************************************************************************/
1344 int32
VSQuerytag(int32 vkey)1345 VSQuerytag(int32 vkey /* IN: vdata key */)
1346 {
1347 vsinstance_t *w = NULL;
1348 VDATA *vs = NULL;
1349 int32 ret_value = SUCCEED;
1350 CONSTR(FUNC, "VSQuerytag");
1351
1352 /* clear error stack */
1353 HEclear();
1354
1355 /* check vdata key is a valid */
1356 if (HAatom_group(vkey) != VSIDGROUP)
1357 HGOTO_ERROR(DFE_ARGS,FAIL);
1358
1359 /* get vdata instance */
1360 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1361 HGOTO_ERROR(DFE_NOVS,FAIL);
1362
1363 /* get Vdata itself and check */
1364 vs = w->vs;
1365 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1366 HGOTO_ERROR(DFE_ARGS,FAIL);
1367
1368 /* return otag of vdata */
1369 ret_value = ((int32) vs->otag);
1370
1371 done:
1372 if(ret_value == FAIL)
1373 { /* Error condition cleanup */
1374
1375 } /* end if */
1376
1377 /* Normal function cleanup */
1378
1379 return ret_value;
1380 } /* VSQuerytag */
1381
1382 /*******************************************************************************
1383 NAME
1384 VSQueryref
1385
1386 DESCRIPTION
1387 get the ref of the the given Vdata
1388
1389 RETURNS
1390 Return the ref of the given Vdata
1391 Return FAIL on failure
1392
1393 *******************************************************************************/
1394 int32
VSQueryref(int32 vkey)1395 VSQueryref(int32 vkey /* IN: vdata key */)
1396 {
1397 vsinstance_t *w = NULL;
1398 VDATA *vs = NULL;
1399 int32 ret_value = SUCCEED;
1400 CONSTR(FUNC, "VSQueryref");
1401
1402 /* clear error stack */
1403 HEclear();
1404
1405 /* check vdata key is a valid */
1406 if (HAatom_group(vkey) != VSIDGROUP)
1407 HGOTO_ERROR(DFE_ARGS,FAIL);
1408
1409 /* get vdata instance */
1410 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1411 HGOTO_ERROR(DFE_NOVS,FAIL);
1412
1413 /* get Vdata itself and check */
1414 vs = w->vs;
1415 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1416 HGOTO_ERROR(DFE_ARGS,FAIL);
1417
1418 /* return ref of vdata */
1419 ret_value = ((int32) vs->oref);
1420
1421 done:
1422 if(ret_value == FAIL)
1423 { /* Error condition cleanup */
1424
1425 } /* end if */
1426
1427 /* Normal function cleanup */
1428
1429 return ret_value;
1430 } /* VSQueryref */
1431
1432 /*******************************************************************************
1433 NAME
1434 vswritelist
1435
1436 DESCRIPTION
1437 get the 'writelist' of the given vdata
1438
1439 RETURNS
1440 return the 'writelist' of the vdata if successful else NULL
1441
1442 *******************************************************************************/
1443 DYN_VWRITELIST *
vswritelist(int32 vkey)1444 vswritelist(int32 vkey /* IN: vdata key */)
1445 {
1446 vsinstance_t *w = NULL;
1447 VDATA *vs = NULL;
1448 DYN_VWRITELIST *ret_value = NULL; /* Failure */
1449 CONSTR(FUNC, "VSwritelist");
1450
1451 /* clear error stack */
1452 HEclear();
1453
1454 /* check vdata key is a valid */
1455 if (HAatom_group(vkey) != VSIDGROUP)
1456 HGOTO_ERROR(DFE_ARGS, NULL);
1457
1458 /* get vdata instance */
1459 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1460 HGOTO_ERROR(DFE_NOVS, NULL);
1461
1462 /* get Vdata itself and check */
1463 vs = w->vs;
1464 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1465 HGOTO_ERROR(DFE_ARGS, NULL);
1466
1467 /* return 'writelist' */
1468 ret_value = (&(vs->wlist));
1469
1470 done:
1471 if(ret_value == NULL)
1472 { /* Error condition cleanup */
1473
1474 } /* end if */
1475
1476 /* Normal function cleanup */
1477
1478 return ret_value;
1479 } /* vswritelist() */
1480
1481 /*******************************************************************************
1482 NAME
1483 VSgetversion
1484
1485 DESCRIPTION
1486 get the version nuber of the vdata
1487
1488 RETURNS
1489 return the version number if successful else '0'.
1490
1491 *******************************************************************************/
1492 int32
VSgetversion(int32 vkey)1493 VSgetversion(int32 vkey /* IN: vdata key */)
1494 {
1495 vsinstance_t *w = NULL;
1496 VDATA *vs = NULL;
1497 int32 ret_value = SUCCEED;
1498 CONSTR(FUNC, "VSgetversion");
1499
1500 /* clear error stack */
1501 HEclear();
1502
1503 /* check vdata key is a valid */
1504 if (HAatom_group(vkey) != VSIDGROUP)
1505 HGOTO_ERROR(DFE_ARGS, 0);
1506
1507 /* get vdata instance */
1508 if (NULL == (w = (vsinstance_t *) HAatom_object(vkey)))
1509 HGOTO_ERROR(DFE_NOVS, 0);
1510
1511 /* get Vdata itself and check */
1512 vs = w->vs;
1513 if ((vs == NULL) || (vs->otag != VSDESCTAG))
1514 HGOTO_ERROR(DFE_ARGS, 0);
1515
1516 /* return version number */
1517 ret_value = (int32)vs->version;
1518
1519 done:
1520 if(ret_value == FAIL)
1521 { /* Error condition cleanup */
1522
1523 } /* end if */
1524
1525 /* Normal function cleanup */
1526
1527 return ret_value;
1528 } /* end VSgetversion() */
1529
1530 /*******************************************************************************
1531 NAME
1532 VSdelete
1533
1534 DESCRIPTION
1535 Remove a Vdata from its file. This function will both remove the Vdata
1536 from the internal Vset data structures as well as from the file.
1537 'vsid' is actually the 'ref' of the vdata.
1538
1539 (i.e. it calls tbbt_delete() and Hdeldd())
1540
1541 RETURNS
1542 Return FAIL / SUCCEED
1543
1544 *******************************************************************************/
1545 int32
VSdelete(int32 f,int32 vsid)1546 VSdelete(int32 f, /* IN: file handle */
1547 int32 vsid /* IN: vdata id i.e. ref */)
1548 {
1549 void * v;
1550 vfile_t *vf = NULL;
1551 void * *t = NULL;
1552 int32 key;
1553 int32 ret_value = SUCCEED;
1554 CONSTR(FUNC, "VSdelete");
1555
1556 /* clear error stack */
1557 HEclear();
1558
1559 /* check valid vdata id */
1560 if (vsid < -1)
1561 HGOTO_ERROR(DFE_ARGS, FAIL);
1562
1563 /* get vdata file record */
1564 if (NULL == (vf = Get_vfile(f)))
1565 HGOTO_ERROR(DFE_FNF,FAIL);
1566
1567 /* find vdata in TBBT using it's ref */
1568 key = vsid;
1569 if (( t = (void * *) tbbtdfind(vf->vstree, &key, NULL))== NULL)
1570 HGOTO_DONE(FAIL);
1571
1572 /* remove vdata from TBBT */
1573 v = tbbtrem((TBBT_NODE **) vf->vstree, (TBBT_NODE *) t, NULL);
1574
1575 /* destroy vdata node itself*/
1576 if (v != NULL)
1577 vsdestroynode(v);
1578
1579 /* delete vdata header and data from file */
1580 if (Hdeldd(f, DFTAG_VS, (uint16) vsid) == FAIL)
1581 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1582
1583 if (Hdeldd(f, DFTAG_VH, (uint16) vsid) == FAIL)
1584 HGOTO_ERROR(DFE_INTERNAL, FAIL);
1585
1586 done:
1587 if(ret_value == FAIL)
1588 { /* Error condition cleanup */
1589
1590 } /* end if */
1591
1592 /* Normal function cleanup */
1593 return ret_value;
1594 } /* VSdelete */
1595