diff options
Diffstat (limited to 'tools/lib')
-rw-r--r-- | tools/lib/Makefile.in | 2 | ||||
-rw-r--r-- | tools/lib/h5tools.h | 3 | ||||
-rw-r--r-- | tools/lib/h5tools_ref.c | 306 | ||||
-rw-r--r-- | tools/lib/h5tools_ref.h | 49 | ||||
-rw-r--r-- | tools/lib/h5tools_str.c | 21 |
5 files changed, 378 insertions, 3 deletions
diff --git a/tools/lib/Makefile.in b/tools/lib/Makefile.in index 070bdcc..2fff656 100644 --- a/tools/lib/Makefile.in +++ b/tools/lib/Makefile.in @@ -41,7 +41,7 @@ PROGS=$(PUB_PROGS) $(TEST_PROGS) ## Source and object files for the library; do not install ## -LIB_SRC=h5tools.c h5tools_str.c h5tools_utils.c h5diff.c h5diff_array.c h5diff_attr.c h5diff_dset.c h5diff_util.c h5trav.c h5trav_table.c h5tools_filters.c +LIB_SRC=h5tools.c h5tools_str.c h5tools_utils.c h5diff.c h5diff_array.c h5diff_attr.c h5diff_dset.c h5diff_util.c h5trav.c h5trav_table.c h5tools_filters.c h5tools_ref.c LIB_OBJ=$(LIB_SRC:.c=.lo) PUB_LIB= AUX_LIB=$(LIB) diff --git a/tools/lib/h5tools.h b/tools/lib/h5tools.h index 545db02..d561a94 100644 --- a/tools/lib/h5tools.h +++ b/tools/lib/h5tools.h @@ -318,6 +318,9 @@ typedef struct h5dump_t { /*print array indices in output matrix */ int pindex; + /*interpret CR/LF information */ + int do_lf; + } h5dump_t; typedef struct dump_header{ diff --git a/tools/lib/h5tools_ref.c b/tools/lib/h5tools_ref.c new file mode 100644 index 0000000..7dcccad --- /dev/null +++ b/tools/lib/h5tools_ref.c @@ -0,0 +1,306 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by the Board of Trustees of the University of Illinois. * + * All rights reserved. * + * * + * This file is part of HDF5. The full HDF5 copyright notice, including * + * terms governing use, modification, and redistribution, is contained in * + * the files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdf.ncsa.uiuc.edu/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from hdfhelp@ncsa.uiuc.edu. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#include <stdio.h> +#include <stdlib.h> +#include "h5tools_ref.h" +#include "H5private.h" +#include "h5tools.h" +#include "h5tools_utils.h" + + +/* + * Table to look up a path name for an object + * reference. + * + * This table stores mappings of reference -> path + * for all objects in the file that may be the target of + * an object reference. + * + * The 'path' is an absolute path by which the object + * can be accessed. When an object has > 1 such path, + * only one will be used in the table, with no particular + * method of selecting which one. + */ + + +extern hid_t thefile; +extern char *prefix; +extern char *progname; +extern int d_status; + + + +ref_path_table_entry_t *ref_path_table = NULL; /* the table */ + +/*------------------------------------------------------------------------- + * Function: ref_path_table_lookup + * + * Purpose: Looks up a table entry given a path name. + * Used during construction of the table. + * + * Return: The table entre (pte) or NULL if not in the + * table. + * + * Programmer: REMcG + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +ref_path_table_entry_t * +ref_path_table_lookup(const char *thepath) +{ + H5G_stat_t sb; + ref_path_table_entry_t *pte = ref_path_table; + + if(H5Gget_objinfo(thefile, thepath, TRUE, &sb)<0) { + /* fatal error ? */ + return NULL; + } + + while(pte!=NULL) { + if (sb.objno==pte->statbuf.objno) + return pte; + pte = pte->next; + } + + return NULL; +} + +/*------------------------------------------------------------------------- + * Function: ref_path_table_put + * + * Purpose: Enter the 'obj' with 'path' in the table if + * not already there. + * Create an object reference, pte, and store them + * in the table. + * + * Return: The object reference for the object. + * + * Programmer: REMcG + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +ref_path_table_entry_t * +ref_path_table_put(hid_t obj, const char *path) +{ + ref_path_table_entry_t *pte; + + /* look up 'obj'. If already in table, return */ + pte = ref_path_table_lookup(path); + if (pte != NULL) + return pte; + + /* if not found, then make new entry */ + + pte = (ref_path_table_entry_t *) malloc(sizeof(ref_path_table_entry_t)); + if (pte == NULL) { + /* fatal error? */ + return NULL; + } + + pte->obj = obj; + + pte->apath = HDstrdup(path); + + if(H5Gget_objinfo(thefile, path, TRUE, &pte->statbuf)<0) { + /* fatal error? */ + free(pte); + return NULL; + } + + pte->next = ref_path_table; + ref_path_table = pte; + + return pte; +} + +/* + * counter used to disambiguate multiple instances of same object. + */ +int xid = 1; + +int get_next_xid() { + return xid++; +} + +/* + * This counter is used to create fake object ID's + * The idea is to set it to the largest possible offest, which + * minimizes the chance of collision with a real object id. + * + */ +haddr_t fake_xid = HADDR_MAX; +haddr_t +get_fake_xid () { + return (fake_xid--); +} + +/* + * for an object that does not have an object id (e.g., soft link), + * create a table entry with a fake object id as the key. + */ + +ref_path_table_entry_t * +ref_path_table_gen_fake(const char *path) +{ + ref_path_table_entry_t *pte; + + /* look up 'obj'. If already in table, return */ + pte = ref_path_table_lookup(path); + if (pte != NULL) { + return pte; + } + + /* if not found, then make new entry */ + + pte = (ref_path_table_entry_t *) malloc(sizeof(ref_path_table_entry_t)); + if (pte == NULL) { + /* fatal error? */ + return NULL; + } + + pte->obj = (hid_t)-1; + + memset(&pte->statbuf,0,sizeof(H5G_stat_t)); + pte->statbuf.objno = get_fake_xid(); + + pte->apath = HDstrdup(path); + + pte->next = ref_path_table; + ref_path_table = pte; + + return pte; +} + +/*------------------------------------------------------------------------- + * Function: lookup_ref_path + * + * Purpose: Lookup the path to the object with refernce 'ref'. + * + * Return: Return a path to the object, or NULL if not found. + * + * Programmer: REMcG + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +char * +lookup_ref_path(hobj_ref_t ref) +{ + ref_path_table_entry_t *pte = ref_path_table; + + while(pte!=NULL) { + if (ref==pte->statbuf.objno) + return pte->apath; + pte = pte->next; + } + return NULL; +} + +/*------------------------------------------------------------------------- + * Function: fill_ref_path_table + * + * Purpose: Called by interator to create references for + * all objects and enter them in the table. + * + * Return: Error status. + * + * Programmer: REMcG + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +fill_ref_path_table(hid_t group, const char *name, void UNUSED * op_data) +{ + hid_t obj; + char *tmp; + H5G_stat_t statbuf; + ref_path_table_entry_t *pte; + char *thepath; + + H5Gget_objinfo(group, name, FALSE, &statbuf); + tmp = (char *) malloc(strlen(prefix) + strlen(name) + 2); + + if (tmp == NULL) + return FAIL; + + thepath = (char *) malloc(strlen(prefix) + strlen(name) + 2); + + if (thepath == NULL) { + free(tmp); + return FAIL; + } + + strcpy(tmp, prefix); + + strcpy(thepath, prefix); + strcat(thepath, "/"); + strcat(thepath, name); + + switch (statbuf.type) { + case H5G_DATASET: + if ((obj = H5Dopen(group, name)) >= 0) { + pte = ref_path_table_lookup(thepath); + if (pte == NULL) { + ref_path_table_put(obj, thepath); + } + H5Dclose(obj); + } else { + error_msg(progname, "unable to get dataset \"%s\"\n", name); + d_status = EXIT_FAILURE; + } + break; + case H5G_GROUP: + if ((obj = H5Gopen(group, name)) >= 0) { + strcat(strcat(prefix, "/"), name); + pte = ref_path_table_lookup(thepath); + if (pte == NULL) { + ref_path_table_put(obj, thepath); + H5Giterate(obj, ".", NULL, fill_ref_path_table, NULL); + strcpy(prefix, tmp); + } + H5Gclose(obj); + } else { + error_msg(progname, "unable to dump group \"%s\"\n", name); + d_status = EXIT_FAILURE; + } + break; + case H5G_TYPE: + if ((obj = H5Topen(group, name)) >= 0) { + pte = ref_path_table_lookup(thepath); + if (pte == NULL) { + ref_path_table_put(obj, thepath); + } + H5Tclose(obj); + } else { + error_msg(progname, "unable to get dataset \"%s\"\n", name); + d_status = EXIT_FAILURE; + } + break; + default: + break; + } + + free(tmp); + free(thepath); + return 0; +} + diff --git a/tools/lib/h5tools_ref.h b/tools/lib/h5tools_ref.h new file mode 100644 index 0000000..2f5fa83 --- /dev/null +++ b/tools/lib/h5tools_ref.h @@ -0,0 +1,49 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by the Board of Trustees of the University of Illinois. * + * All rights reserved. * + * * + * This file is part of HDF5. The full HDF5 copyright notice, including * + * terms governing use, modification, and redistribution, is contained in * + * the files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdf.ncsa.uiuc.edu/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from hdfhelp@ncsa.uiuc.edu. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +#ifndef H5TOOLS_REF_H__ +#define H5TOOLS_REF_H__ + +#include "hdf5.h" + +typedef struct ref_path_table_entry_t { + hid_t obj; + hobj_ref_t *obj_ref; + char *apath; + H5G_stat_t statbuf; + struct ref_path_table_entry_t *next; +}ref_path_table_entry_t; + +#ifdef __cplusplus +extern "C" { +#endif + + +char* lookup_ref_path(hobj_ref_t ref); +herr_t fill_ref_path_table(hid_t, const char *, void *); +int get_next_xid(void); +haddr_t get_fake_xid (void); +struct ref_path_table_entry_t *ref_path_table_lookup(const char *); +ref_path_table_entry_t *ref_path_table_put(hid_t obj, const char *path); +struct ref_path_table_entry_t *ref_path_table_gen_fake(const char *); + +#ifdef __cplusplus +} +#endif + + + +#endif + + diff --git a/tools/lib/h5tools_str.c b/tools/lib/h5tools_str.c index 5398d76..fb1d0c2 100644 --- a/tools/lib/h5tools_str.c +++ b/tools/lib/h5tools_str.c @@ -27,6 +27,9 @@ #include "h5tools.h" /*for h5dump_t structure */ #include "h5tools_str.h" /*function prototypes */ +extern char* lookup_ref_path(hobj_ref_t ref); + + /* * If REPEAT_VERBOSE is defined then character strings will be printed so * that repeated character sequences like "AAAAAAAAAA" are displayed as @@ -452,8 +455,13 @@ h5tools_print_char(h5tools_str_t *str, const h5dump_t *info, unsigned char ch) h5tools_str_append(str, "\\f"); break; case '\n': - h5tools_str_append(str, "\\n"); - break; + if (info->do_lf) { + h5tools_str_append(str, "\n"); + h5tools_str_append(str, " "); + } + else + h5tools_str_append(str, "\\n"); + break; case '\r': h5tools_str_append(str, "\\r"); break; @@ -794,6 +802,7 @@ h5tools_str_sprint(h5tools_str_t *str, const h5dump_t *info, hid_t container, if (h5tools_is_zero(vp, H5Tget_size(type))) { h5tools_str_append(str, "NULL"); } else { + char *path=NULL; otype = H5Rget_obj_type(container, H5R_OBJECT, vp); obj = H5Rdereference(container, H5R_OBJECT, vp); H5Gget_objinfo(obj, ".", FALSE, &sb); @@ -822,6 +831,14 @@ h5tools_str_sprint(h5tools_str_t *str, const h5dump_t *info, hid_t container, h5tools_str_append(str, info->obj_format, sb.objno); else h5tools_str_append(str, info->obj_format, sb.fileno,sb.objno); + + /* Print name */ + path = lookup_ref_path(*(hobj_ref_t *)vp); + if (path) { + h5tools_str_append(str, " "); + h5tools_str_append(str, path); + h5tools_str_append(str, " "); + } } } else if (H5Tget_class(type) == H5T_ARRAY) { int k, ndims; |