summaryrefslogtreecommitdiffstats
path: root/src/H5Gloc.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/H5Gloc.c')
-rw-r--r--src/H5Gloc.c469
1 files changed, 469 insertions, 0 deletions
diff --git a/src/H5Gloc.c b/src/H5Gloc.c
new file mode 100644
index 0000000..e2a293f
--- /dev/null
+++ b/src/H5Gloc.c
@@ -0,0 +1,469 @@
+/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+ * 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. *
+ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
+
+/*-------------------------------------------------------------------------
+ *
+ * Created: H5Gloc.c
+ * Sep 13 2005
+ * Quincey Koziol <koziol@ncsa.uiuc.edu>
+ *
+ * Purpose: Functions for working with group "locations"
+ *
+ *-------------------------------------------------------------------------
+ */
+#define H5G_PACKAGE /*suppress error about including H5Gpkg */
+
+
+/* Packages needed by this file... */
+#include "H5private.h" /* Generic Functions */
+#include "H5Aprivate.h" /* Attributes */
+#include "H5Dprivate.h" /* Datasets */
+#include "H5Eprivate.h" /* Error handling */
+#include "H5Gpkg.h" /* Groups */
+#include "H5Iprivate.h" /* IDs */
+
+/* Private typedefs */
+
+/* User data for looking up an object in a group */
+typedef struct {
+ H5G_loc_t *loc; /* Group location to set */
+} H5G_loc_ud1_t;
+
+/* Private macros */
+
+/* Local variables */
+
+/* PRIVATE PROTOTYPES */
+static herr_t H5G_loc_find_cb(H5G_loc_t *grp_loc, const char *name,
+ const H5O_link_t *lnk, H5G_loc_t *obj_loc, void *_udata);
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc
+ *
+ * Purpose: Given an object ID return a location for the object.
+ *
+ * Return: Success: Group pointer.
+ * Failure: NULL
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc(hid_t loc_id, H5G_loc_t *loc)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc, FAIL)
+
+ switch(H5I_get_type(loc_id)) {
+ case H5I_FILE:
+ {
+ H5F_t *f;
+
+ if(NULL == (f = H5I_object(loc_id)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid file ID")
+ if(NULL == (loc->oloc = H5G_oloc(H5G_rootof(f))))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry for root group")
+ if(NULL == (loc->path = H5G_nameof(H5G_rootof(f))))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path for root group")
+
+ /* Patch up root group's symbol table entry to reflect this file */
+ /* (Since the root group info is only stored once for files which
+ * share an underlying low-level file)
+ */
+ /* (but only for non-mounted files) */
+ if(!H5F_is_mount(f))
+ loc->oloc->file = f;
+ } /* end case */
+ break;
+
+ case H5I_GENPROP_CLS:
+ case H5I_GENPROP_LST:
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of property list")
+
+ case H5I_ERROR_CLASS:
+ case H5I_ERROR_MSG:
+ case H5I_ERROR_STACK:
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of error class, message or stack")
+
+ case H5I_GROUP:
+ {
+ H5G_t *group;
+
+ if(NULL == (group = H5I_object(loc_id)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid group ID")
+ if(NULL == (loc->oloc = H5G_oloc(group)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of group")
+ if(NULL == (loc->path = H5G_nameof(group)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path of group")
+ } /* end case */
+ break;
+
+ case H5I_DATATYPE:
+ {
+ H5T_t *dt;
+
+ if(NULL == (dt = H5I_object(loc_id)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid type ID")
+ if(NULL == (loc->oloc = H5T_oloc(dt)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of datatype")
+ if(NULL == (loc->path = H5T_nameof(dt)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path of datatype")
+ } /* end case */
+ break;
+
+ case H5I_DATASPACE:
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of dataspace")
+
+ case H5I_DATASET:
+ {
+ H5D_t *dset;
+
+ if(NULL == (dset = H5I_object(loc_id)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid data ID")
+ if(NULL == (loc->oloc = H5D_oloc(dset)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of dataset")
+ if(NULL == (loc->path = H5D_nameof(dset)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path of dataset")
+ } /* end case */
+ break;
+
+ case H5I_ATTR:
+ {
+ H5A_t *attr;
+
+ if(NULL == (attr = H5I_object(loc_id)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid attribute ID")
+ if(NULL == (loc->oloc = H5A_oloc(attr)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of attribute")
+ if(NULL == (loc->path = H5A_nameof(attr)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path of attribute")
+ } /* end case */
+ break;
+
+ case H5I_REFERENCE:
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get symbol table entry of reference")
+
+ default:
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid object ID")
+ } /* end switch */
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_copy
+ *
+ * Purpose: Copy over information for a location
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_copy(H5G_loc_t *dst, H5G_loc_t *src, H5G_copy_depth_t depth)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_copy, FAIL)
+
+ /* Check args. */
+ HDassert(dst);
+ HDassert(src);
+
+ /* Copy components of the location */
+ if(H5O_loc_copy(dst->oloc, src->oloc, (depth == H5G_COPY_SHALLOW ? H5O_COPY_SHALLOW : H5O_COPY_DEEP)) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to copy entry")
+ if(H5G_name_copy(dst->path, src->path, depth) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to copy path")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_copy() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_reset
+ *
+ * Purpose: Reset information for a location
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_reset(H5G_loc_t *loc)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_reset, FAIL)
+
+ /* Check args. */
+ HDassert(loc);
+
+ /* Reset components of the location */
+ if(H5O_loc_reset(loc->oloc) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to reset entry")
+ if(H5G_name_reset(loc->path) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to reset path")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_reset() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_free
+ *
+ * Purpose: Free information for a location
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_free(H5G_loc_t *loc)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_free, FAIL)
+
+ /* Check args. */
+ HDassert(loc);
+
+ /* Reset components of the location */
+#ifdef NOT_YET
+ if(H5G_ent_free(loc->ent) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to free entry")
+#endif /* NOT_YET */
+ if(H5G_name_free(loc->path) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTOPENOBJ, FAIL, "unable to free path")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_free() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_find_cb
+ *
+ * Purpose: Callback for retrieving object location for an object in a group
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Monday, October 17, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+H5G_loc_find_cb(H5G_loc_t UNUSED *grp_loc/*in*/, const char UNUSED *name, const H5O_link_t UNUSED *lnk,
+ H5G_loc_t *obj_loc, void *_udata/*in,out*/)
+{
+ H5G_loc_ud1_t *udata = (H5G_loc_ud1_t *)_udata; /* User data passed in */
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT(H5G_loc_find_cb)
+
+ /* Check if the name in this group resolved to a valid link */
+ if(obj_loc == NULL)
+ HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "name doesn't exist")
+
+ /* Take ownership of the object's group location */
+ /* (Group traversal callbacks are responsible for either taking ownership
+ * of the group location for the object, or freeing it. - QAK)
+ */
+ H5G_loc_copy(udata->loc, obj_loc, H5O_COPY_SHALLOW);
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_find_cb() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_find
+ *
+ * Purpose: Find a symbol from a location
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_find(H5G_loc_t *loc, const char *name, H5G_loc_t *obj_loc/*out*/,
+ hid_t dxpl_id)
+{
+ H5G_loc_ud1_t udata; /* User data for traversal callback */
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_find, FAIL)
+
+ /* Check args. */
+ HDassert(loc);
+ HDassert(name && *name);
+ HDassert(obj_loc);
+
+ /* Set up user data for locating object */
+ udata.loc = obj_loc;
+
+ /* Traverse group hierarchy to locate object */
+ if(H5G_traverse(loc, name, H5G_TARGET_NORMAL, H5G_loc_find_cb, &udata, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "can't find object")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_find() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_insert
+ *
+ * Purpose: Insert an object at a location
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Tuesday, September 13, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_insert(H5G_loc_t *grp_loc, const char *name, H5G_loc_t *obj_loc,
+ hbool_t inc_link, hid_t dxpl_id)
+{
+ H5O_link_t lnk; /* Link for object to insert */
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_insert, FAIL)
+
+ /* Check args. */
+ HDassert(grp_loc);
+ HDassert(name && *name);
+ HDassert(obj_loc);
+
+ /* "Translate" object location into link object */
+ lnk.type = H5G_LINK_HARD;
+#ifdef H5_HAVE_GETTIMEOFDAY
+ {
+ struct timeval now_tv;
+
+ HDgettimeofday(&now_tv, NULL);
+ lnk.ctime = now_tv.tv_sec;
+ }
+#else /* H5_HAVE_GETTIMEOFDAY */
+ lnk.ctime = HDtime(NULL);
+#endif /* H5_HAVE_GETTIMEOFDAY */
+ lnk.cset = H5T_CSET_ASCII; /* XXX: Allow user to set this */
+ /* Casting away const OK -QAK */
+ lnk.name = (char *)name;
+ lnk.u.hard.addr = obj_loc->oloc->addr;
+
+ /* Insert new group into current group's symbol table */
+ if(H5G_obj_insert(grp_loc->oloc, name, &lnk, inc_link, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTINSERT, FAIL, "unable to insert object")
+
+ /* Set the name of the object location */
+ if(H5G_name_set(grp_loc->path, obj_loc->path, name) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTINIT, FAIL, "cannot set name")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_insert() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_exists
+ *
+ * Purpose: Check if a symbol exists in a location
+ *
+ * Return: Non-negative if object exists/Negative if object doesn't exist
+ *
+ * Programmer: Quincey Koziol
+ * Monday, September 19, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_exists(const H5G_loc_t *loc, const char *name, hid_t dxpl_id)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_exists, FAIL)
+
+ /* Check args. */
+ HDassert(loc);
+ HDassert(name && *name);
+
+ /* Get information for object in current group */
+ if(H5G_obj_lookup(loc->oloc, name, NULL, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "component not found")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_exists() */
+
+
+/*-------------------------------------------------------------------------
+ * Function: H5G_loc_remove
+ *
+ * Purpose: Remove a link from a group
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ * Programmer: Quincey Koziol
+ * Monday, September 19, 2005
+ *
+ *-------------------------------------------------------------------------
+ */
+herr_t
+H5G_loc_remove(H5G_loc_t *grp_loc, const char *name, H5G_loc_t *obj_loc, hid_t dxpl_id)
+{
+ H5G_obj_t obj_type; /* Type of object removed */
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI(H5G_loc_remove, FAIL)
+
+ /* Check args. */
+ HDassert(grp_loc);
+ HDassert(name && *name);
+
+ /* Remove object from group */
+ if(H5G_obj_remove(grp_loc->oloc, name, &obj_type, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "component not found")
+
+ /* Search the open IDs and replace names for unlinked object */
+ if(H5G_name_replace(obj_type, obj_loc, NULL, NULL, NULL, NULL, OP_UNLINK) < 0)
+ HGOTO_ERROR(H5E_SYM, H5E_CANTDELETE, FAIL, "unable to replace name")
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5G_loc_remove() */
+