summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJerome Soumagne <jsoumagne@hdfgroup.org>2015-12-03 18:33:11 (GMT)
committerJerome Soumagne <jsoumagne@hdfgroup.org>2016-11-29 23:42:31 (GMT)
commitf545fa003ec9319a2ac1a9b299c605adb7a86ad9 (patch)
tree00b7f137bbd01c0ce00b473bba352e314eef7122
parent4e0eb46e0629dc33b0b953883bc605e753dbc8c2 (diff)
downloadhdf5-f545fa003ec9319a2ac1a9b299c605adb7a86ad9.zip
hdf5-f545fa003ec9319a2ac1a9b299c605adb7a86ad9.tar.gz
hdf5-f545fa003ec9319a2ac1a9b299c605adb7a86ad9.tar.bz2
Add external references
Remove dataset region reference and use new region reference instead Fix reference conversion code Modify reference API to use opaque type
-rwxr-xr-xbin/trace2
-rw-r--r--src/H5Aint.c11
-rw-r--r--src/H5Dchunk.c10
-rw-r--r--src/H5Dcompact.c11
-rw-r--r--src/H5Dcontig.c13
-rw-r--r--src/H5Dio.c5
-rw-r--r--src/H5Ocopy.c199
-rw-r--r--src/H5Odtype.c17
-rw-r--r--src/H5Oprivate.h3
-rw-r--r--src/H5R.c1546
-rw-r--r--src/H5Rdeprec.c12
-rw-r--r--src/H5Rpkg.h8
-rw-r--r--src/H5Rprivate.h24
-rw-r--r--src/H5Rpublic.h62
-rw-r--r--src/H5T.c132
-rw-r--r--src/H5Tconv.c96
-rw-r--r--src/H5Tnative.c47
-rw-r--r--src/H5Tpkg.h7
-rw-r--r--src/H5Tpublic.h8
-rw-r--r--src/H5Tref.c291
-rw-r--r--src/H5detect.c10
-rw-r--r--src/H5trace.c10
22 files changed, 1403 insertions, 1121 deletions
diff --git a/bin/trace b/bin/trace
index 1d6b318..768a94a 100755
--- a/bin/trace
+++ b/bin/trace
@@ -78,7 +78,7 @@ $Source = "";
"H5Q_type_t" => "Qt",
"H5Q_match_op_t" => "Qm",
"H5Q_combine_op_t" => "Qc",
- "hobj_ref_t" => "r",
+ "href_t" => "r",
"H5R_type_t" => "Rt",
"char" => "s",
"unsigned char" => "s",
diff --git a/src/H5Aint.c b/src/H5Aint.c
index cd5408d..6937758 100644
--- a/src/H5Aint.c
+++ b/src/H5Aint.c
@@ -2279,15 +2279,8 @@ H5A_attr_post_copy_file(const H5O_loc_t *src_oloc, const H5A_t *attr_src,
/* Check for expanding references */
if(cpy_info->expand_ref) {
- size_t ref_count;
-
- /* Determine # of reference elements to copy */
- ref_count = attr_dst->shared->data_size / H5T_get_size(attr_dst->shared->dt);
-
- /* Copy objects referenced in source buffer to destination file and set destination elements */
- if(H5O_copy_expand_ref(file_src, attr_dst->shared->data, dxpl_id,
- file_dst, attr_dst->shared->data, ref_count, H5T_get_ref_type(attr_dst->shared->dt), cpy_info) < 0)
- HGOTO_ERROR(H5E_ATTR, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
+ /* TODO needs to be implemented (should use H5Tconvert) */
+ HGOTO_ERROR(H5E_ATTR, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
} /* end if */
else
/* Reset value to zero */
diff --git a/src/H5Dchunk.c b/src/H5Dchunk.c
index 7e73a4a..9c1df42 100644
--- a/src/H5Dchunk.c
+++ b/src/H5Dchunk.c
@@ -4772,14 +4772,8 @@ H5D__chunk_copy_cb(const H5D_chunk_rec_t *chunk_rec, void *_udata)
/* Check for expanding references */
/* (background buffer has already been zeroed out, if not expanding) */
if(udata->cpy_info->expand_ref) {
- size_t ref_count;
-
- /* Determine # of reference elements to copy */
- ref_count = nbytes / H5T_get_size(udata->dt_src);
-
- /* Copy the reference elements */
- if(H5O_copy_expand_ref(udata->file_src, buf, udata->idx_info_dst->dxpl_id, udata->idx_info_dst->f, bkg, ref_count, H5T_get_ref_type(udata->dt_src), udata->cpy_info) < 0)
- HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, H5_ITER_ERROR, "unable to copy reference attribute")
+ /* TODO needs to be implemented (should use H5Tconvert) */
+ HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, H5_ITER_ERROR, "unable to copy reference attribute")
} /* end if */
/* After fix ref, copy the new reference elements to the buffer to write out */
diff --git a/src/H5Dcompact.c b/src/H5Dcompact.c
index ebe75bd..20d80cb 100644
--- a/src/H5Dcompact.c
+++ b/src/H5Dcompact.c
@@ -556,15 +556,8 @@ H5D__compact_copy(H5F_t *f_src, H5O_storage_compact_t *storage_src, H5F_t *f_dst
if(f_src != f_dst) {
/* Check for expanding references */
if(cpy_info->expand_ref) {
- size_t ref_count;
-
- /* Determine # of reference elements to copy */
- ref_count = storage_src->size / H5T_get_size(dt_src);
-
- /* Copy objects referenced in source buffer to destination file and set destination elements */
- if(H5O_copy_expand_ref(f_src, storage_src->buf, dxpl_id, f_dst,
- storage_dst->buf, ref_count, H5T_get_ref_type(dt_src), cpy_info) < 0)
- HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
+ /* TODO needs to be implemented (should use H5Tconvert) */
+ HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
} /* end if */
else
/* Reset value to zero */
diff --git a/src/H5Dcontig.c b/src/H5Dcontig.c
index 988bb61..78c6f43 100644
--- a/src/H5Dcontig.c
+++ b/src/H5Dcontig.c
@@ -1546,17 +1546,8 @@ H5D__contig_copy(H5F_t *f_src, const H5O_storage_contig_t *storage_src,
else if(fix_ref) {
/* Check for expanding references */
if(cpy_info->expand_ref) {
- size_t ref_count;
-
- /* Determine # of reference elements to copy */
- ref_count = src_nbytes / H5T_get_size(dt_src);
-
- /* Copy the reference elements */
- if(H5O_copy_expand_ref(f_src, buf, dxpl_id, f_dst, bkg, ref_count, H5T_get_ref_type(dt_src), cpy_info) < 0)
- HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
-
- /* After fix ref, copy the new reference elements to the buffer to write out */
- HDmemcpy(buf, bkg, buf_size);
+ /* TODO needs to be implemented (should use H5Tconvert) */
+ HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "unable to copy reference attribute")
} /* end if */
else
/* Reset value to zero */
diff --git a/src/H5Dio.c b/src/H5Dio.c
index 138c746..cfbcb9e 100644
--- a/src/H5Dio.c
+++ b/src/H5Dio.c
@@ -720,9 +720,8 @@ H5D__write(H5D_t *dataset, hid_t mem_type_id, const H5S_t *mem_space,
/* We should really use H5T_detect_class() here, but it will be difficult
* to detect the type of the reference if it is nested... -QAK
*/
- if(H5T_get_class(type_info.mem_type, TRUE) == H5T_REFERENCE &&
- H5T_get_ref_type(type_info.mem_type) == H5R_DATASET_REGION)
- HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "Parallel IO does not support writing region reference datatypes yet")
+ if(H5T_get_class(type_info.mem_type, TRUE) == H5T_REFERENCE)
+ HGOTO_ERROR(H5E_DATASET, H5E_UNSUPPORTED, FAIL, "Parallel IO does not support writing reference datatypes yet")
/* Can't write to chunked datasets with filters, in parallel */
if(dataset->shared->layout.type == H5D_CHUNKED &&
diff --git a/src/H5Ocopy.c b/src/H5Ocopy.c
index e641d70..4488cd1 100644
--- a/src/H5Ocopy.c
+++ b/src/H5Ocopy.c
@@ -88,8 +88,6 @@ static herr_t H5O_copy_header(const H5O_loc_t *oloc_src, H5O_loc_t *oloc_dst /*o
hid_t dxpl_id, hid_t ocpypl_id);
static herr_t H5O_copy_obj(H5G_loc_t *src_loc, H5G_loc_t *dst_loc,
const char *dst_name, hid_t ocpypl_id, hid_t lcpl_id, hid_t dxpl_id);
-static herr_t H5O_copy_obj_by_ref(H5O_loc_t *src_oloc, hid_t dxpl_id,
- H5O_loc_t *dst_oloc, H5G_loc_t *dst_root_loc, H5O_copy_t *cpy_info);
static herr_t H5O_copy_free_comm_dt_cb(void *item, void *key, void *op_data);
static int H5O_copy_comm_dt_cmp(const void *dt1, const void *dt2);
static herr_t H5O_copy_search_comm_dt_cb(hid_t group, const char *name,
@@ -1203,203 +1201,6 @@ done:
/*-------------------------------------------------------------------------
- * Function: H5O_copy_obj_by_ref
- *
- * Purpose: Copy the object pointed by _src_ref.
- *
- * Return: Non-negative on success/Negative on failure
- *
- * Programmer: Peter Cao
- * Aug 7 2006
- *
- *-------------------------------------------------------------------------
- */
-static herr_t
-H5O_copy_obj_by_ref(H5O_loc_t *src_oloc, hid_t dxpl_id, H5O_loc_t *dst_oloc,
- H5G_loc_t *dst_root_loc, H5O_copy_t *cpy_info)
-{
- herr_t ret_value = SUCCEED;
-
- FUNC_ENTER_NOAPI(FAIL)
-
- HDassert(src_oloc);
- HDassert(dst_oloc);
-
- /* Perform the copy, or look up existing copy */
- if((ret_value = H5O_copy_header_map(src_oloc, dst_oloc, dxpl_id, cpy_info,
- FALSE, NULL, NULL)) < 0)
- HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "unable to copy object")
-
- /* Check if a new valid object is copied to the destination */
- if(H5F_addr_defined(dst_oloc->addr) && (ret_value > SUCCEED)) {
- char tmp_obj_name[80];
- H5G_name_t new_path;
- H5O_loc_t new_oloc;
- H5G_loc_t new_loc;
-
- /* Set up group location for new object */
- new_loc.oloc = &new_oloc;
- new_loc.path = &new_path;
- H5G_loc_reset(&new_loc);
- new_oloc.file = dst_oloc->file;
- new_oloc.addr = dst_oloc->addr;
-
- /* Pick a default name for the new object */
- HDsnprintf(tmp_obj_name, sizeof(tmp_obj_name), "~obj_pointed_by_%llu", (unsigned long long)dst_oloc->addr);
-
- /* Create a link to the newly copied object */
- /* Note: since H5O_copy_header_map actually copied the target object, it
- * must exist either in cache or on disk, therefore it is is safe to not
- * pass the obj_type and udata fields returned by H5O_copy_header_map.
- * This could be changed in the future to slightly improve performance
- * --NAF */
- if(H5L_link(dst_root_loc, tmp_obj_name, &new_loc, H5P_DEFAULT, H5P_DEFAULT, dxpl_id) < 0)
- HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "unable to insert link")
-
- H5G_loc_free(&new_loc);
- } /* if (H5F_addr_defined(dst_oloc.addr)) */
-
-done:
- FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5O_copy_obj_by_ref() */
-
-
-/*-------------------------------------------------------------------------
- * Function: H5O_copy_expand_ref
- *
- * Purpose: Copy the object pointed by _src_ref.
- *
- * Return: Non-negative on success/Negative on failure
- *
- * Programmer: Peter Cao
- * Aug 7 2006
- *
- *-------------------------------------------------------------------------
- */
-herr_t
-H5O_copy_expand_ref(H5F_t *file_src, void *_src_ref, hid_t dxpl_id,
- H5F_t *file_dst, void *_dst_ref, size_t ref_count, H5R_type_t ref_type,
- H5O_copy_t *cpy_info)
-{
- H5O_loc_t dst_oloc; /* Copied object object location */
- H5O_loc_t src_oloc; /* Temporary object location for source object */
- H5G_loc_t dst_root_loc; /* The location of root group of the destination file */
- const uint8_t *q; /* Pointer to source OID to store */
- uint8_t *p; /* Pointer to destination OID to store */
- size_t i; /* Local index variable */
- herr_t ret_value = SUCCEED;
-
- FUNC_ENTER_NOAPI(FAIL)
-
- /* Sanity checks */
- HDassert(file_src);
- HDassert(_src_ref);
- HDassert(file_dst);
- HDassert(_dst_ref);
- HDassert(ref_count);
- HDassert(cpy_info);
-
- /* Initialize object locations */
- H5O_loc_reset(&src_oloc);
- H5O_loc_reset(&dst_oloc);
- src_oloc.file = file_src;
- dst_oloc.file = file_dst;
-
- /* Set up the root group in the destination file */
- if(NULL == (dst_root_loc.oloc = H5G_oloc(H5G_rootof(file_dst))))
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get object location for root group")
- if(NULL == (dst_root_loc.path = H5G_nameof(H5G_rootof(file_dst))))
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "unable to get path for root group")
-
- /* Copy object references */
- if(H5R_OBJECT == ref_type) {
- hobj_ref_t *src_ref = (hobj_ref_t *)_src_ref;
- hobj_ref_t *dst_ref = (hobj_ref_t *)_dst_ref;
-
- /* Making equivalent references in the destination file */
- for(i = 0; i < ref_count; i++) {
- /* Set up for the object copy for the reference */
- q = (uint8_t *)(&src_ref[i]);
- H5F_addr_decode(src_oloc.file, (const uint8_t **)&q, &(src_oloc.addr));
- dst_oloc.addr = HADDR_UNDEF;
-
- /* Attempt to copy object from source to destination file */
- if(src_oloc.addr != (haddr_t)0) {
- if(H5O_copy_obj_by_ref(&src_oloc, dxpl_id, &dst_oloc, &dst_root_loc, cpy_info) < 0)
- HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "unable to copy object")
- } /* end if */
- else
- /* Set parameters so the reference is written as all 0's */
- HDmemset(&dst_oloc.addr, 0, sizeof(dst_oloc.addr));
-
- /* Set the object reference info for the destination file */
- p = (uint8_t *)(&dst_ref[i]);
- H5F_addr_encode(dst_oloc.file, &p, dst_oloc.addr);
- } /* end for */
- } /* end if */
- /* Copy region references */
- else if(H5R_DATASET_REGION == ref_type) {
- hdset_reg_ref_t *src_ref = (hdset_reg_ref_t *)_src_ref;
- hdset_reg_ref_t *dst_ref = (hdset_reg_ref_t *)_dst_ref;
- uint8_t *buf = NULL; /* Buffer to store serialized selection in */
- H5HG_t hobjid; /* Heap object ID */
- size_t buf_size; /* Length of object in heap */
-
- /* Making equivalent references in the destination file */
- for(i = 0; i < ref_count; i++) {
- /* Get the heap ID for the dataset region */
- q = (const uint8_t *)(&src_ref[i]);
- H5F_addr_decode(src_oloc.file, (const uint8_t **)&q, &(hobjid.addr));
- UINT32DECODE(q, hobjid.idx);
-
- if(hobjid.addr != (haddr_t)0) {
- /* Get the dataset region from the heap (allocate inside routine) */
- if((buf = (uint8_t *)H5HG_read(src_oloc.file, dxpl_id, &hobjid, NULL, &buf_size)) == NULL)
- HGOTO_ERROR(H5E_REFERENCE, H5E_READERROR, FAIL, "Unable to read dataset region information")
-
- /* Get the object oid for the dataset */
- q = (const uint8_t *)buf;
- H5F_addr_decode(src_oloc.file, (const uint8_t **)&q, &(src_oloc.addr));
- dst_oloc.addr = HADDR_UNDEF;
-
- /* copy the object pointed by the ref to the destination */
- if(H5O_copy_obj_by_ref(&src_oloc, dxpl_id, &dst_oloc, &dst_root_loc, cpy_info) < 0) {
- H5MM_xfree(buf);
- HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "unable to copy object")
- } /* end if */
-
- /* Serialize object ID */
- p = (uint8_t *)buf;
- H5F_addr_encode(dst_oloc.file, &p, dst_oloc.addr);
-
- /* Save the serialized buffer to the destination */
- if(H5HG_insert(dst_oloc.file, dxpl_id, buf_size, buf, &hobjid) < 0) {
- H5MM_xfree(buf);
- HGOTO_ERROR(H5E_OHDR, H5E_CANTCOPY, FAIL, "Unable to write dataset region information")
- } /* end if */
- } /* end if */
- else
- /* Set parameters so the reference is written as all 0's */
- HDmemset(&hobjid, 0, sizeof(hobjid));
-
- /* Set the dataset region reference info for the destination file */
- p = (uint8_t *)(&dst_ref[i]);
- H5F_addr_encode(dst_oloc.file, &p, hobjid.addr);
- UINT32ENCODE(p, hobjid.idx);
-
- /* Free the buffer allocated in H5HG_read() */
- H5MM_xfree(buf);
- } /* end for */
- } /* end if */
- else
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
-
-done:
- FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5O_copy_expand_ref() */
-
-
-/*-------------------------------------------------------------------------
* Function: H5O_copy_free_comm_dt_cb
*
* Purpose: Frees the merge committed dt skip list key and object.
diff --git a/src/H5Odtype.c b/src/H5Odtype.c
index 748ff70..5091614 100644
--- a/src/H5Odtype.c
+++ b/src/H5Odtype.c
@@ -438,17 +438,12 @@ H5O_dtype_decode_helper(H5F_t *f, unsigned *ioflags/*in,out*/, const uint8_t **p
/* Set reference type */
dt->shared->u.atomic.u.r.rtype = (H5R_type_t)(flags & 0x0f);
- /* Set extra information for object references, so the hobj_ref_t gets swizzled correctly */
- if(dt->shared->u.atomic.u.r.rtype == H5R_OBJECT
- || dt->shared->u.atomic.u.r.rtype == H5R_REGION
- || dt->shared->u.atomic.u.r.rtype == H5R_ATTR) {
- /* Mark location this type as undefined for now. The caller function should
- * decide the location. */
- dt->shared->u.atomic.u.r.loc = H5T_LOC_BADLOC;
-
- /* This type needs conversion */
- dt->shared->force_conv = TRUE;
- } /* end if */
+ /* Mark location this type as undefined for now. The caller function should
+ * decide the location. */
+ dt->shared->u.atomic.u.r.loc = H5T_LOC_BADLOC;
+
+ /* This type needs conversion */
+ dt->shared->force_conv = TRUE;
break;
case H5T_ENUM:
diff --git a/src/H5Oprivate.h b/src/H5Oprivate.h
index 1f71be6..23a05ff 100644
--- a/src/H5Oprivate.h
+++ b/src/H5Oprivate.h
@@ -828,9 +828,6 @@ H5_DLL herr_t H5O_msg_unlock(const H5O_loc_t *loc, unsigned type_id, hid_t dxpl_
H5_DLL herr_t H5O_copy_header_map(const H5O_loc_t *oloc_src, H5O_loc_t *oloc_dst /*out */,
hid_t dxpl_id, H5O_copy_t *cpy_info, hbool_t inc_depth,
H5O_type_t *obj_type, void **udata);
-H5_DLL herr_t H5O_copy_expand_ref(H5F_t *file_src, void *_src_ref, hid_t dxpl_id,
- H5F_t *file_dst, void *_dst_ref, size_t ref_count, H5R_type_t ref_type,
- H5O_copy_t *cpy_info);
/* Debugging routines */
H5_DLL herr_t H5O_debug_id(unsigned type_id, H5F_t *f, hid_t dxpl_id, const void *mesg, FILE *stream, int indent, int fwidth);
diff --git a/src/H5R.c b/src/H5R.c
index 0819597..7112785 100644
--- a/src/H5R.c
+++ b/src/H5R.c
@@ -17,23 +17,23 @@
/* Module Setup */
/****************/
-#include "H5Rmodule.h" /* This source code file is part of the H5R module */
+#include "H5Rmodule.h" /* This source code file is part of the H5R module */
/***********/
/* Headers */
/***********/
-#include "H5private.h" /* Generic Functions */
-#include "H5ACprivate.h" /* Metadata cache */
-#include "H5Aprivate.h" /* Attributes */
-#include "H5Dprivate.h" /* Datasets */
-#include "H5Eprivate.h" /* Error handling */
-#include "H5Gprivate.h" /* Groups */
-#include "H5HGprivate.h" /* Global Heaps */
-#include "H5Iprivate.h" /* IDs */
-#include "H5MMprivate.h" /* Memory management */
-#include "H5Rpkg.h" /* References */
-#include "H5Sprivate.h" /* Dataspaces */
+#include "H5private.h" /* Generic Functions */
+#include "H5ACprivate.h" /* Metadata cache */
+#include "H5Aprivate.h" /* Attributes */
+#include "H5Dprivate.h" /* Datasets */
+#include "H5Eprivate.h" /* Error handling */
+#include "H5Gprivate.h" /* Groups */
+#include "H5HGprivate.h" /* Global Heaps */
+#include "H5Iprivate.h" /* IDs */
+#include "H5MMprivate.h" /* Memory management */
+#include "H5Rpkg.h" /* References */
+#include "H5Sprivate.h" /* Dataspaces */
/****************/
@@ -41,7 +41,6 @@
/****************/
#define H5R_MAX_ATTR_REF_NAME_LEN (64 * 1024)
-
/******************/
/* Local Typedefs */
/******************/
@@ -51,9 +50,10 @@
/* Local Prototypes */
/********************/
-static H5S_t * H5R_get_region(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type, const void *_ref);
-static ssize_t H5R_get_name(H5F_t *file, hid_t lapl_id, hid_t dxpl_id, hid_t id,
- H5R_type_t ref_type, const void *_ref, char *name, size_t size);
+static H5S_t * H5R__get_region(H5F_t *file, hid_t dxpl_id, const href_t *_ref);
+static ssize_t H5R__get_name(H5F_t *file, hid_t lapl_id, hid_t dxpl_id, hid_t id,
+ const href_t *_ref, char *name, size_t size);
+static ssize_t H5R__get_filename(const href_t *ref, char *name, size_t size);
/*********************/
@@ -84,7 +84,6 @@ static const H5I_class_t H5I_REFERENCE_CLS[1] = {{
/* Flag indicating "top" of interface has been initialized */
static hbool_t H5R_top_package_initialize_s = FALSE;
-
/*--------------------------------------------------------------------------
NAME
@@ -203,517 +202,805 @@ H5R_term_package(void)
/*--------------------------------------------------------------------------
NAME
- H5R_create
+ H5R_create_object
PURPOSE
Creates a particular kind of reference for the user
USAGE
- herr_t H5R_create(ref, ref_type, ...)
- void *ref; OUT: Reference created
- H5R_type_t ref_type; IN: Type of reference to create
- Additional arguments:
- H5G_loc_t *loc; IN: File location used to locate object pointed to
- const char *name; IN: Name of object at location of object pointed to
- hid_t dxpl_id; IN: Property list ID
- H5S_t *space; IN: Dataspace with selection, used for Dataset
- Region references.
- const char *attr_name; IN: Name of attribute pointed to, used for
- Attribute references.
+ href_t *H5R_create_object(loc, name, dxpl_id)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
RETURNS
- Non-negative on success/Negative on failure
+ Reference created on success/NULL on failure
DESCRIPTION
Creates a particular type of reference specified with REF_TYPE, in the
- space pointed to by REF. The LOC_ID and NAME are used to locate the object
- pointed to and the SPACE_ID is used to choose the region pointed to (for
- Dataset Region references) or ATTR_NAME is used to choose tha attribute
- pointed to (for Attribute references).
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
+ space pointed to by REF. The LOC and NAME are used to locate the object
+ pointed to.
--------------------------------------------------------------------------*/
-herr_t
-H5R_create(void *_ref, H5R_type_t ref_type, ...)
+href_t *
+H5R_create_object(H5G_loc_t *loc, const char *name, hid_t dxpl_id)
{
H5G_loc_t obj_loc; /* Group hier. location of object */
H5G_name_t path; /* Object group hier. path */
H5O_loc_t oloc; /* Object object location */
- uint8_t *buf = NULL; /* Buffer to store serialized selection in */
hbool_t obj_found = FALSE; /* Object location found */
- va_list ap;
- herr_t ret_value = SUCCEED; /* Return value */
+ href_t *ret_value = NULL; /* Return value */
FUNC_ENTER_NOAPI_NOINIT
- HDassert(ref_type > H5R_BADTYPE && ref_type < H5R_MAXTYPE);
+ HDassert(loc);
+ HDassert(name);
+
+ /* Set up object location to fill in */
+ obj_loc.oloc = &oloc;
+ obj_loc.path = &path;
+ H5G_loc_reset(&obj_loc);
+
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
+
+ if(NULL == (ret_value = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+
+ ret_value->ref_type = H5R_OBJECT;
+ ret_value->obj_addr = obj_loc.oloc->addr;
+
+done:
+ if(obj_found)
+ H5G_loc_free(&obj_loc);
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5R_create_object() */
- va_start(ap, ref_type);
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_create_region
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5R_create_region(loc, name, dxpl_id, space)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
+ H5S_t *space; IN: Dataspace with selection, used for Dataset
+ Region references.
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC and NAME are used to locate the object
+ pointed to and the SPACE is used to choose the region pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5R_create_region(H5G_loc_t *loc, const char *name, hid_t dxpl_id, H5S_t *space)
+{
+ H5G_loc_t obj_loc; /* Group hier. location of object */
+ H5G_name_t path; /* Object group hier. path */
+ H5O_loc_t oloc; /* Object object location */
+ hbool_t obj_found = FALSE; /* Object location found */
+ hssize_t buf_size; /* Size of buffer needed to serialize selection */
+ uint8_t *p; /* Pointer to OID to store */
+ href_t *ref = NULL; /* Reference to be returned */
+ href_t *ret_value = NULL; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT
+
+ HDassert(loc);
+ HDassert(name);
+ HDassert(space);
/* Set up object location to fill in */
obj_loc.oloc = &oloc;
obj_loc.path = &path;
H5G_loc_reset(&obj_loc);
- switch(ref_type) {
- case H5R_OBJECT:
- {
- H5G_loc_t *loc;
- const char *name;
- hid_t dxpl_id;
- hobj_ref_t *ref = (hobj_ref_t *)_ref; /* Get pointer to correct type of reference struct */
-
- /* Get arguments */
- loc = va_arg(ap, H5G_loc_t *);
- name = va_arg(ap, const char *);
- dxpl_id = va_arg(ap, hid_t);
-
- HDassert(ref);
- HDassert(loc);
- HDassert(name);
-
- /* Find the object */
- if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, FAIL, "object not found")
- obj_found = TRUE;
-
- *ref = obj_loc.oloc->addr;
- break;
- }
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
- case H5R_DATASET_REGION:
- {
- H5G_loc_t *loc;
- const char *name;
- hid_t dxpl_id;
- H5HG_t hobjid; /* Heap object ID */
- hdset_reg_ref_t *ref = (hdset_reg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- hssize_t buf_size; /* Size of buffer needed to serialize selection */
- uint8_t *p; /* Pointer to OID to store */
- hbool_t heapid_found; /* Flag for non-zero heap ID found */
- unsigned u; /* local index */
- H5S_t *space;
-
- /* Get arguments */
- loc = va_arg(ap, H5G_loc_t *);
- name = va_arg(ap, const char *);
- dxpl_id = va_arg(ap, hid_t);
- space = va_arg(ap, H5S_t *);
-
- HDassert(ref);
- HDassert(loc);
- HDassert(name);
- HDassert(space);
-
- /* Find the object */
- if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, FAIL, "object not found")
- obj_found = TRUE;
-
- /* Set up information for dataset region */
-
- /* Return any previous heap block to the free list if we are garbage collecting */
- if(H5F_GC_REF(loc->oloc->file)) {
- /* Check for an existing heap ID in the reference */
- for(u = 0, heapid_found = FALSE, p = (uint8_t *)ref; u < H5R_DSET_REG_REF_BUF_SIZE; u++)
- if(p[u] != 0) {
- heapid_found = TRUE;
- break;
- } /* end if */
+ /* Get the amount of space required to serialize the selection */
+ if((buf_size = H5S_SELECT_SERIAL_SIZE(space)) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, NULL, "Invalid amount of space for serializing selection")
- if(heapid_found) {
-/* Return heap block to free list */
- } /* end if */
- } /* end if */
+ /* Increase buffer size to allow for the dataset OID */
+ buf_size += (hssize_t)sizeof(haddr_t);
- /* Zero the heap ID out, may leak heap space if user is re-using reference and doesn't have garbage collection on */
- HDmemset(ref, 0, H5R_DSET_REG_REF_BUF_SIZE);
+ /* Allocate the space to store the serialized information */
+ H5_CHECK_OVERFLOW(buf_size, hssize_t, size_t);
+ if(NULL == (ref = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+ if (NULL == (ref->obj_enc.buf = H5MM_malloc((size_t) buf_size)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "Cannot allocate buffer to serialize selection")
+ ref->obj_enc.buf_size = (size_t) buf_size;
+ ref->ref_type = H5R_REGION;
- /* Get the amount of space required to serialize the selection */
- if((buf_size = H5S_SELECT_SERIAL_SIZE(space)) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "Invalid amount of space for serializing selection")
+ /* Serialize information for dataset OID into buffer */
+ p = (uint8_t *)ref->obj_enc.buf;
+ H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
- /* Increase buffer size to allow for the dataset OID */
- buf_size += (hssize_t)sizeof(haddr_t);
+ /* Serialize the selection into buffer */
+ if(H5S_SELECT_SERIALIZE(space, &p) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCOPY, NULL, "Unable to serialize selection")
- /* Allocate the space to store the serialized information */
- H5_CHECK_OVERFLOW(buf_size, hssize_t, size_t);
- if(NULL == (buf = (uint8_t *)H5MM_malloc((size_t)buf_size)))
- HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed")
+ ret_value = ref;
- /* Serialize information for dataset OID into heap buffer */
- p = (uint8_t *)buf;
- H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
+done:
+ if(obj_found)
+ H5G_loc_free(&obj_loc);
+ if(NULL == ret_value) {
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+ }
- /* Serialize the selection into heap buffer */
- if(H5S_SELECT_SERIALIZE(space, &p) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCOPY, FAIL, "Unable to serialize selection")
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* H5R_create_region */
- /* Save the serialized buffer for later */
- if(H5HG_insert(loc->oloc->file, dxpl_id, (size_t)buf_size, buf, &hobjid) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_WRITEERROR, FAIL, "Unable to serialize selection")
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_create_attr
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5R_create_attr(loc, name, dxpl_id, attr_name)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
+ const char *attr_name; IN: Name of attribute pointed to, used for
+ Attribute references.
- /* Serialize the heap ID and index for storage in the file */
- p = (uint8_t *)ref;
- H5F_addr_encode(loc->oloc->file, &p, hobjid.addr);
- UINT32ENCODE(p, hobjid.idx);
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC, NAME and ATTR_NAME are used to locate
+ the attribute pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5R_create_attr(H5G_loc_t *loc, const char *name, hid_t dxpl_id, const char *attr_name)
+{
+ H5G_loc_t obj_loc; /* Group hier. location of object */
+ H5G_name_t path; /* Object group hier. path */
+ H5O_loc_t oloc; /* Object object location */
+ hbool_t obj_found = FALSE; /* Object location found */
+ size_t buf_size; /* Size of buffer needed to serialize attribute */
+ size_t attr_name_len; /* Length of the attribute name */
+ uint8_t *p; /* Pointer to OID to store */
+ href_t *ref = NULL; /* Reference to be returned */
+ href_t *ret_value = NULL; /* Return value */
- break;
- }
+ FUNC_ENTER_NOAPI_NOINIT
- case H5R_REGION:
- {
- H5G_loc_t *loc;
- const char *name;
- hid_t dxpl_id;
- hreg_ref_t *ref = (hreg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- hssize_t buf_size; /* Size of buffer needed to serialize selection */
- uint8_t *p; /* Pointer to OID to store */
- H5S_t *space;
-
- /* Get arguments */
- loc = va_arg(ap, H5G_loc_t *);
- name = va_arg(ap, const char *);
- dxpl_id = va_arg(ap, hid_t);
- space = va_arg(ap, H5S_t *);
-
- HDassert(ref);
- HDassert(loc);
- HDassert(name);
- HDassert(space);
-
- /* Find the object */
- if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, FAIL, "object not found")
- obj_found = TRUE;
-
- /* Get the amount of space required to serialize the selection */
- if((buf_size = H5S_SELECT_SERIAL_SIZE(space)) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "Invalid amount of space for serializing selection")
-
- /* Increase buffer size to allow for the dataset OID */
- buf_size += (hssize_t)sizeof(haddr_t);
-
- /* Allocate the space to store the serialized information */
- H5_CHECK_OVERFLOW(buf_size, hssize_t, size_t);
-
- if(!ref->buf || ref->buf_size < (size_t) buf_size) {
- ref->buf_size = (size_t)buf_size;
- } else {
- /* Serialize information for dataset OID into buffer */
- p = (uint8_t *)ref->buf;
- H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
-
- /* Serialize the selection into buffer */
- if(H5S_SELECT_SERIALIZE(space, &p) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCOPY, FAIL, "Unable to serialize selection")
- }
- }
- break;
+ HDassert(loc);
+ HDassert(name);
+ HDassert(attr_name);
- case H5R_ATTR:
- {
- H5G_loc_t *loc;
- const char *name;
- hid_t dxpl_id;
- hattr_ref_t *ref = (hattr_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- size_t buf_size; /* Size of buffer needed to serialize attribute */
- size_t attr_name_len; /* Length of the attribute name */
- uint8_t *p; /* Pointer to OID to store */
- const char *attr_name;
-
- /* Get arguments */
- loc = va_arg(ap, H5G_loc_t *);
- name = va_arg(ap, const char *);
- dxpl_id = va_arg(ap, hid_t);
- attr_name = va_arg(ap, const char *);
-
- HDassert(ref);
- HDassert(loc);
- HDassert(name);
- HDassert(attr_name);
-
- /* Find the object */
- if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, FAIL, "object not found")
- obj_found = TRUE;
-
- /* Get the amount of space required to serialize the attribute name */
- attr_name_len = HDstrlen(attr_name);
- if(attr_name_len >= H5R_MAX_ATTR_REF_NAME_LEN)
- HGOTO_ERROR(H5E_REFERENCE, H5E_ARGS, FAIL, "attribute name too long")
-
- /* Compute buffer size, allow for the attribute name length and object's OID */
- buf_size = attr_name_len + 2 + sizeof(haddr_t);
-
- /* Allocate the space to store the serialized information */
- if(!ref->buf || ref->buf_size < buf_size) {
- ref->buf_size = buf_size;
- } else {
- /* Serialize information for object's OID into buffer */
- p = (uint8_t *)ref->buf;
- H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
-
- /* Serialize information for attribute name length into the buffer */
- UINT16ENCODE(p, attr_name_len);
-
- /* Copy the attribute name into the buffer */
- HDmemcpy(p, attr_name, attr_name_len);
-
- /* Sanity check */
- HDassert((size_t)((p + attr_name_len) - (uint8_t *)ref->buf) == buf_size);
- }
- }
- break;
+ /* Set up object location to fill in */
+ obj_loc.oloc = &oloc;
+ obj_loc.path = &path;
+ H5G_loc_reset(&obj_loc);
- case H5R_BADTYPE:
- case H5R_MAXTYPE:
- default:
- HDassert("unknown reference type" && 0);
- HGOTO_ERROR(H5E_REFERENCE, H5E_UNSUPPORTED, FAIL, "internal error (unknown reference type)")
- } /* end switch */
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
+
+ /* Get the amount of space required to serialize the attribute name */
+ attr_name_len = HDstrlen(attr_name);
+ if(attr_name_len >= H5R_MAX_ATTR_REF_NAME_LEN)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_ARGS, NULL, "attribute name too long")
+
+ /* Compute buffer size, allow for the attribute name length and object's OID */
+ buf_size = attr_name_len + 2 + sizeof(haddr_t);
+
+ /* Allocate the space to store the serialized information */
+ if(NULL == (ref = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+ if (NULL == (ref->obj_enc.buf = H5MM_malloc((size_t) buf_size)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "Cannot allocate buffer to serialize selection")
+ ref->obj_enc.buf_size = (size_t) buf_size;
+ ref->ref_type = H5R_ATTR;
+
+ /* Serialize information for object's OID into buffer */
+ p = (uint8_t *)ref->obj_enc.buf;
+ H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
+
+ /* Serialize information for attribute name length into the buffer */
+ UINT16ENCODE(p, attr_name_len);
+
+ /* Copy the attribute name into the buffer */
+ HDmemcpy(p, attr_name, attr_name_len);
+
+ /* Sanity check */
+ HDassert((size_t)((p + attr_name_len) - (uint8_t *)ref->obj_enc.buf) == buf_size);
+
+ ret_value = ref;
+
+done:
+ if(obj_found)
+ H5G_loc_free(&obj_loc);
+ if(NULL == ret_value) {
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+ }
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* H5R_create_attr */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_create_ext_object
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5R_create_ext_object(loc, name, dxpl_id)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC and NAME are used to locate the object
+ pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5R_create_ext_object(H5G_loc_t *loc, const char *name, hid_t dxpl_id)
+{
+ H5G_loc_t obj_loc; /* Group hier. location of object */
+ H5G_name_t path; /* Object group hier. path */
+ H5O_loc_t oloc; /* Object object location */
+ hbool_t obj_found = FALSE; /* Object location found */
+ size_t filename_len; /* Length of the file name */
+ size_t buf_size; /* Size of buffer needed to serialize reference */
+ uint8_t *p; /* Pointer to OID to store */
+ href_t *ref = NULL; /* Reference to be returned */
+ href_t *ret_value = NULL; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT
+
+ HDassert(loc);
+ HDassert(name);
+
+ /* Set up object location to fill in */
+ obj_loc.oloc = &oloc;
+ obj_loc.path = &path;
+ H5G_loc_reset(&obj_loc);
+
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
+
+ /* Need to add name of the file */
+ filename_len = HDstrlen(H5F_OPEN_NAME(loc->oloc->file));
+
+ /* Compute buffer size, allow for the attribute name length and object's OID */
+ buf_size = filename_len + 2 + sizeof(haddr_t);
+
+ if(NULL == (ref = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+ if (NULL == (ref->obj_enc.buf = H5MM_malloc((size_t) buf_size)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "Cannot allocate buffer to serialize selection")
+ ref->obj_enc.buf_size = (size_t) buf_size;
+ ref->ref_type = H5R_EXT_OBJECT;
+
+ /* Serialize information for file name length into the buffer */
+ p = (uint8_t *)ref->obj_enc.buf;
+ UINT16ENCODE(p, filename_len);
+
+ /* Copy the file name into the buffer */
+ HDmemcpy(p, H5F_OPEN_NAME(loc->oloc->file), filename_len);
+ p += filename_len;
+
+ /* Serialize information for object's OID into buffer */
+ H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
+
+ ret_value = ref;
done:
if(obj_found)
H5G_loc_free(&obj_loc);
+ if(NULL == ret_value) {
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+ }
- H5MM_free(buf);
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5R_create_ext_object() */
- va_end(ap);
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_create_ext_region
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5R_create_ext_region(loc, name, dxpl_id, space)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
+ H5S_t *space; IN: Dataspace with selection, used for Dataset
+ Region references.
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC and NAME are used to locate the object
+ pointed to and the SPACE is used to choose the region pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5R_create_ext_region(H5G_loc_t *loc, const char *name, hid_t dxpl_id, H5S_t *space)
+{
+ H5G_loc_t obj_loc; /* Group hier. location of object */
+ H5G_name_t path; /* Object group hier. path */
+ H5O_loc_t oloc; /* Object object location */
+ hbool_t obj_found = FALSE; /* Object location found */
+ size_t filename_len; /* Length of the file name */
+ hssize_t buf_size; /* Size of buffer needed to serialize selection */
+ uint8_t *p; /* Pointer to OID to store */
+ href_t *ref = NULL; /* Reference to be returned */
+ href_t *ret_value = NULL; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT
+
+ HDassert(loc);
+ HDassert(name);
+ HDassert(space);
+
+ /* Set up object location to fill in */
+ obj_loc.oloc = &oloc;
+ obj_loc.path = &path;
+ H5G_loc_reset(&obj_loc);
+
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
+
+ /* Need to add name of the file */
+ filename_len = HDstrlen(H5F_OPEN_NAME(loc->oloc->file));
+
+ /* Get the amount of space required to serialize the selection */
+ if((buf_size = H5S_SELECT_SERIAL_SIZE(space)) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, NULL, "Invalid amount of space for serializing selection")
+
+ /* Increase buffer size to allow for the dataset OID */
+ buf_size += (hssize_t)(sizeof(haddr_t) + 2 + filename_len);
+
+ /* Allocate the space to store the serialized information */
+ H5_CHECK_OVERFLOW(buf_size, hssize_t, size_t);
+ if(NULL == (ref = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+ if (NULL == (ref->obj_enc.buf = H5MM_malloc((size_t) buf_size)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "Cannot allocate buffer to serialize selection")
+ ref->obj_enc.buf_size = (size_t) buf_size;
+ ref->ref_type = H5R_EXT_REGION;
+
+ /* Serialize information for file name length into the buffer */
+ p = (uint8_t *)ref->obj_enc.buf;
+ UINT16ENCODE(p, filename_len);
+
+ /* Copy the file name into the buffer */
+ HDmemcpy(p, H5F_OPEN_NAME(loc->oloc->file), filename_len);
+ p += filename_len;
+
+ /* Serialize information for dataset OID into buffer */
+ H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
+
+ /* Serialize the selection into buffer */
+ if(H5S_SELECT_SERIALIZE(space, &p) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCOPY, NULL, "Unable to serialize selection")
+
+ ret_value = ref;
+
+done:
+ if(obj_found)
+ H5G_loc_free(&obj_loc);
+ if(NULL == ret_value) {
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+ }
FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5R_create() */
+} /* H5R_create_ext_region */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_create_ext_attr
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5R_create_ext_attr(loc, name, dxpl_id, attr_name)
+ H5G_loc_t *loc; IN: File location used to locate object pointed to
+ const char *name; IN: Name of object at location of object pointed to
+ hid_t dxpl_id; IN: Property list ID
+ const char *attr_name; IN: Name of attribute pointed to, used for
+ Attribute references.
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC, NAME and ATTR_NAME are used to locate
+ the attribute pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5R_create_ext_attr(H5G_loc_t *loc, const char *name, hid_t dxpl_id, const char *attr_name)
+{
+ H5G_loc_t obj_loc; /* Group hier. location of object */
+ H5G_name_t path; /* Object group hier. path */
+ H5O_loc_t oloc; /* Object object location */
+ hbool_t obj_found = FALSE; /* Object location found */
+ size_t filename_len; /* Length of the file name */
+ size_t buf_size; /* Size of buffer needed to serialize attribute */
+ size_t attr_name_len; /* Length of the attribute name */
+ uint8_t *p; /* Pointer to OID to store */
+ href_t *ref = NULL; /* Reference to be returned */
+ href_t *ret_value = NULL; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT
+
+ HDassert(loc);
+ HDassert(name);
+ HDassert(attr_name);
+
+ /* Set up object location to fill in */
+ obj_loc.oloc = &oloc;
+ obj_loc.path = &path;
+ H5G_loc_reset(&obj_loc);
+
+ /* Find the object */
+ if(H5G_loc_find(loc, name, &obj_loc, H5P_DEFAULT, dxpl_id) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_NOTFOUND, NULL, "object not found")
+ obj_found = TRUE;
+
+ /* Need to add name of the file */
+ filename_len = HDstrlen(H5F_OPEN_NAME(loc->oloc->file));
+
+ /* Get the amount of space required to serialize the attribute name */
+ attr_name_len = HDstrlen(attr_name);
+ if(attr_name_len >= H5R_MAX_ATTR_REF_NAME_LEN)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_ARGS, NULL, "attribute name too long")
+
+ /* Compute buffer size, allow for the attribute name length and object's OID */
+ buf_size = filename_len + 2 + attr_name_len + 2 + sizeof(haddr_t);
+
+ /* Allocate the space to store the serialized information */
+ if(NULL == (ref = (href_t *)H5MM_malloc(sizeof(href_t))))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "Cannot allocate memory for reference")
+ if (NULL == (ref->obj_enc.buf = H5MM_malloc((size_t) buf_size)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "Cannot allocate buffer to serialize selection")
+ ref->obj_enc.buf_size = (size_t) buf_size;
+ ref->ref_type = H5R_EXT_ATTR;
+
+ /* Serialize information for file name length into the buffer */
+ p = (uint8_t *)ref->obj_enc.buf;
+ UINT16ENCODE(p, filename_len);
+
+ /* Copy the file name into the buffer */
+ HDmemcpy(p, H5F_OPEN_NAME(loc->oloc->file), filename_len);
+ p += filename_len;
+
+ /* Serialize information for object's OID into buffer */
+ H5F_addr_encode(loc->oloc->file, &p, obj_loc.oloc->addr);
+
+ /* Serialize information for attribute name length into the buffer */
+ UINT16ENCODE(p, attr_name_len);
+
+ /* Copy the attribute name into the buffer */
+ HDmemcpy(p, attr_name, attr_name_len);
+
+ /* Sanity check */
+ HDassert((size_t)((p + attr_name_len) - (uint8_t *)ref->obj_enc.buf) == buf_size);
+
+ ret_value = ref;
+
+done:
+ if(obj_found)
+ H5G_loc_free(&obj_loc);
+ if(NULL == ret_value) {
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+ }
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* H5R_create_ext_attr */
/*--------------------------------------------------------------------------
NAME
- H5Rcreate
+ H5Rcreate_object
PURPOSE
Creates a particular kind of reference for the user
USAGE
- herr_t H5Rcreate(ref, ref_type, ...)
- void *ref; OUT: Reference created
- H5R_type_t ref_type; IN: Type of reference to create
- Additional arguments:
- hid_t loc_id; IN: Location ID used to locate object pointed to
- const char *name; IN: Name of object at location LOC_ID of object
- pointed to
- hid_t space_id; IN: Dataspace ID with selection, used for Dataset
- Region references.
- const char *attr_name; IN: Name of attribute pointed to, used for
- Attribute references.
+ href_t *H5Rcreate_object(loc_id, name)
+ hid_t loc_id; IN: Location ID used to locate object pointed to
+ const char *name; IN: Name of object at location LOC_ID of object
+ pointed to
RETURNS
- Non-negative on success/Negative on failure
+ Reference created on success/NULL on failure
DESCRIPTION
Creates a particular type of reference specified with REF_TYPE, in the
space pointed to by REF. The LOC_ID and NAME are used to locate the object
- pointed to and the SPACE_ID is used to choose the region pointed to (for
- Dataset Region references).
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
+ pointed to.
--------------------------------------------------------------------------*/
-herr_t
-H5Rcreate(void *ref, H5R_type_t ref_type, ...)
+href_t *
+H5Rcreate_object(hid_t loc_id, const char *name)
{
- H5S_t *space = NULL; /* Pointer to dataspace containing region */
- va_list ap;
- herr_t ret_value = FAIL; /* Return value */
+ H5G_loc_t loc; /* File location */
+ href_t *ret_value = NULL; /* Return value */
- FUNC_ENTER_API(FAIL)
- H5TRACE2("e", "*xRt", ref, ref_type);
+ FUNC_ENTER_API(NULL)
- va_start(ap, ref_type);
+ /* Check args */
+ if(H5G_loc(loc_id, &loc) < 0)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a location")
+ if(!name || !*name)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "no name given")
+
+ if(NULL == (ret_value = H5R_create_object(&loc, name, H5AC_dxpl_id)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, NULL, "unable to create object reference")
+
+done:
+ FUNC_LEAVE_API(ret_value)
+} /* end H5Rcreate_object() */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5Rcreate_region
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5Rcreate_region(loc_id, name, space_id)
+ hid_t loc_id; IN: Location ID used to locate object pointed to
+ const char *name; IN: Name of object at location LOC_ID of object
+ pointed to
+ hid_t space_id; IN: Dataspace ID with selection, used for Dataset
+ Region references.
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC_ID and NAME are used to locate the object
+ pointed to and the SPACE_ID is used to choose the region pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5Rcreate_region(hid_t loc_id, const char *name, hid_t space_id)
+{
+ H5G_loc_t loc; /* File location */
+ H5S_t *space = NULL; /* Pointer to dataspace containing region */
+ href_t *ret_value = NULL; /* Return value */
+
+ FUNC_ENTER_API(NULL)
/* Check args */
- if(ref == NULL)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(H5G_loc(loc_id, &loc) < 0)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a location")
+ if(!name || !*name)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "no name given")
+ if(space_id == H5I_BADID)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "reference region dataspace id must be valid")
+ if(space_id != H5I_BADID && (NULL == (space = (H5S_t *)H5I_object_verify(space_id, H5I_DATASPACE))))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a dataspace")
+
+ if(NULL == (ret_value = H5R_create_region(&loc, name, H5AC_dxpl_id, space)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, NULL, "unable to create region reference")
- switch (ref_type) {
- case H5R_OBJECT:
- {
- hid_t loc_id;
- H5G_loc_t loc; /* File location */
- const char *name;
+done:
+ FUNC_LEAVE_API(ret_value)
+} /* end H5Rcreate_region() */
- /* Get arguments */
- loc_id = va_arg(ap, hid_t);
- name = va_arg(ap, const char *);
+/*--------------------------------------------------------------------------
+ NAME
+ H5Rcreate_attr
+ PURPOSE
+ Creates a particular kind of reference for the user
+ USAGE
+ href_t *H5Rcreate_attr(loc_id, name, attr_name)
+ hid_t loc_id; IN: Location ID used to locate object pointed to
+ const char *name; IN: Name of object at location LOC_ID of object
+ pointed to
+ const char *attr_name; IN: Name of attribute pointed to, used for
+ Attribute references.
- if(H5G_loc(loc_id, &loc) < 0)
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(!name || !*name)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no name given")
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Creates a particular type of reference specified with REF_TYPE, in the
+ space pointed to by REF. The LOC_ID, NAME and ATTR_NAME are used to locate
+ the attribute pointed to.
+--------------------------------------------------------------------------*/
+href_t *
+H5Rcreate_attr(hid_t loc_id, const char *name, const char *attr_name)
+{
+ H5G_loc_t loc; /* File location */
+ href_t *ret_value = NULL; /* Return value */
- if((ret_value = H5R_create(ref, ref_type, &loc, name, H5AC_dxpl_id)) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to create reference")
- }
- break;
- case H5R_REGION:
- case H5R_DATASET_REGION:
- {
- hid_t loc_id;
- H5G_loc_t loc; /* File location */
- const char *name;
- hid_t space_id;
-
- /* Get arguments */
- loc_id = va_arg(ap, hid_t);
- name = va_arg(ap, const char *);
- space_id = va_arg(ap, hid_t);
-
- if(H5G_loc(loc_id, &loc) < 0)
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(!name || !*name)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no name given")
- if(space_id == H5I_BADID)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "reference region dataspace id must be valid")
- if(space_id != H5I_BADID && (NULL == (space = (H5S_t *)H5I_object_verify(space_id, H5I_DATASPACE))))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace")
- if((ret_value = H5R_create(ref, ref_type, &loc, name, H5AC_dxpl_id, space)) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to create reference")
- }
- break;
- case H5R_ATTR:
- {
- hid_t loc_id;
- H5G_loc_t loc; /* File location */
- const char *name;
- const char *attr_name;
-
- /* Get arguments */
- loc_id = va_arg(ap, hid_t);
- name = va_arg(ap, const char *);
- attr_name = va_arg(ap, const char *);
-
- if(H5G_loc(loc_id, &loc) < 0)
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(!name || !*name)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no name given")
- if(!attr_name || !*attr_name)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no attribute name given")
- if((ret_value = H5R_create(ref, ref_type, &loc, name, H5AC_dxpl_id, attr_name)) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to create reference")
- }
- break;
- case H5R_MAXTYPE:
- case H5R_BADTYPE:
- default:
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
- }
+ FUNC_ENTER_API(NULL)
+
+ /* Check args */
+ if(H5G_loc(loc_id, &loc) < 0)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a location")
+ if(!name || !*name)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "no name given")
+ if(!attr_name || !*attr_name)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, NULL, "no attribute name given")
+
+ if(NULL == (ret_value = H5R_create_attr(&loc, name, H5AC_dxpl_id, attr_name)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, NULL, "unable to create atribute reference")
done:
- va_end(ap);
+ FUNC_LEAVE_API(ret_value)
+} /* end H5Rcreate_attr() */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5R_destroy
+ PURPOSE
+ Destroy a reference
+ USAGE
+ herr_t H5R_destroy(ref)
+ href_t *ref; IN: Reference
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Destroy reference and free resources allocated during H5Rcreate.
+--------------------------------------------------------------------------*/
+herr_t
+H5R_destroy(href_t *ref)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ HDassert(ref);
+
+ if(H5R_OBJECT != ref->ref_type)
+ H5MM_free(ref->obj_enc.buf);
+ H5MM_free(ref);
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5Rdestroy() */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5Rdestroy
+ PURPOSE
+ Destroy a reference
+ USAGE
+ herr_t H5Rdestroy(ref)
+ href_t *ref; IN: Reference
+
+ RETURNS
+ Reference created on success/NULL on failure
+ DESCRIPTION
+ Destroy reference and free resources allocated during H5Rcreate.
+--------------------------------------------------------------------------*/
+herr_t
+H5Rdestroy(href_t *ref)
+{
+ herr_t ret_value = FAIL; /* Return value */
+
+ FUNC_ENTER_API(FAIL)
+
+ /* Check args */
+ if(NULL == ref)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "invalid reference pointer")
+
+ if(FAIL == (ret_value = H5R_destroy(ref)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to destroy reference")
+
+done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rcreate() */
+} /* end H5Rdestroy() */
/*--------------------------------------------------------------------------
NAME
- H5R_dereference
+ H5R__dereference
PURPOSE
Opens the HDF5 object referenced.
USAGE
- hid_t H5R_dereference(ref)
+ hid_t H5R__dereference(file, oapl_id, dxpl_id, ref, app_ref)
H5F_t *file; IN: File the object being dereferenced is within
- H5R_type_t ref_type; IN: Type of reference
- void *ref; IN: Reference to open.
+ hid_t oapl_id; IN: Property list of the object being referenced.
+ hid_t dxpl_id; IN: Property list ID
+ ref_t *ref; IN: Reference to open
+ hbool_t app_ref IN: Referenced by application.
RETURNS
Valid ID on success, Negative on failure
DESCRIPTION
Given a reference to some object, open that object and return an ID for
that object.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- Currently only set up to work with references to datasets
- EXAMPLES
- REVISION LOG
- Raymond Lu
- 13 July 2011
- I added the OAPL_ID parameter for the object being referenced. It only
- supports dataset access property list currently.
-
- M. Scot Breitenfeld
- 3 March 2015
- Added a check for undefined reference pointer.
--------------------------------------------------------------------------*/
hid_t
-H5R_dereference(H5F_t *file, hid_t oapl_id, hid_t dxpl_id, H5R_type_t ref_type, const void *_ref, hbool_t app_ref)
+H5R__dereference(H5F_t *file, hid_t oapl_id, hid_t dxpl_id, const href_t *ref, hbool_t app_ref)
{
- H5O_loc_t oloc; /* Object location */
- H5G_name_t path; /* Path of object */
- H5G_loc_t loc; /* Group location */
- char *attr_name = NULL; /* Name of the attribute (for attribute references) */
- unsigned rc; /* Reference count of object */
- H5O_type_t obj_type; /* Type of object */
- hid_t ret_value = H5I_INVALID_HID; /* Return value */
+ H5O_loc_t oloc; /* Object location */
+ H5G_name_t path; /* Path of object */
+ H5G_loc_t loc; /* Group location */
+ char *filename = NULL; /* Name of the file (for external references) */
+ char *attr_name = NULL; /* Name of the attribute (for attribute references) */
+ unsigned rc; /* Reference count of object */
+ H5O_type_t obj_type; /* Type of object */
+ const uint8_t *p = NULL; /* Pointer to OID to store */
+ hid_t ret_value = H5I_BADID; /* Return value */
FUNC_ENTER_NOAPI_NOINIT
- HDassert(_ref);
- HDassert(ref_type > H5R_BADTYPE && ref_type < H5R_MAXTYPE);
HDassert(file);
+ HDassert(ref);
+ HDassert(ref->ref_type > H5R_BADTYPE && ref->ref_type < H5R_MAXTYPE);
/* Initialize the object location */
H5O_loc_reset(&oloc);
oloc.file = file;
- switch(ref_type) {
- case H5R_OBJECT:
- oloc.addr = *(const hobj_ref_t *)_ref; /* Only object references currently supported */
- if(!H5F_addr_defined(oloc.addr) || oloc.addr == 0)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "Undefined reference pointer")
- break;
-
- case H5R_DATASET_REGION:
+ switch (ref->ref_type) {
+ case H5R_EXT_OBJECT:
+ case H5R_EXT_REGION:
+ case H5R_EXT_ATTR:
{
- H5HG_t hobjid; /* Heap object ID */
- uint8_t *buf; /* Buffer to store serialized selection in */
- const uint8_t *p; /* Pointer to OID to store */
-
- /* Get the heap ID for the dataset region */
- p = (const uint8_t *)_ref;
- H5F_addr_decode(oloc.file, &p, &(hobjid.addr));
- UINT32DECODE(p, hobjid.idx);
+ size_t filename_len; /* Length of the file name */
- if(!H5F_addr_defined(hobjid.addr) || hobjid.addr == 0)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "Undefined reference pointer")
+ /* Get the file name length */
+ p = (const uint8_t *)ref->obj_enc.buf;
+ UINT16DECODE(p, filename_len);
+ HDassert(filename_len < H5R_MAX_ATTR_REF_NAME_LEN);
- /* Get the dataset region from the heap (allocate inside routine) */
- if(NULL == (buf = (uint8_t *)H5HG_read(oloc.file, dxpl_id, &hobjid, NULL, NULL)))
- HGOTO_ERROR(H5E_REFERENCE, H5E_READERROR, FAIL, "Unable to read dataset region information")
+ /* Allocate space for the file name */
+ if(NULL == (filename = (char *)H5MM_malloc(filename_len + 1)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, FAIL, "memory allocation failed")
- /* Get the object oid for the dataset */
- p = buf;
- H5F_addr_decode(oloc.file, &p, &(oloc.addr));
+ /* Get the file name */
+ HDmemcpy(filename, p, filename_len);
+ filename[filename_len] = '\0';
+ p += filename_len;
+ }
+ break;
+ case H5R_OBJECT:
+ case H5R_REGION:
+ case H5R_ATTR:
+ case H5R_BADTYPE:
+ case H5R_MAXTYPE:
+ default:
+ break;
+ }
- /* Free the buffer allocated in H5HG_read() */
- H5MM_xfree(buf);
- } /* end case */
- break;
+ switch(ref->ref_type) {
+ case H5R_OBJECT:
+ oloc.addr = ref->obj_addr;
+ if(!H5F_addr_defined(oloc.addr) || oloc.addr == 0)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "Undefined reference pointer")
+ break;
+ case H5R_EXT_OBJECT:
+ case H5R_EXT_REGION:
case H5R_REGION:
{
- const hreg_ref_t *ref = (const hreg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- const uint8_t *p; /* Pointer to OID to store */
-
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ if (!p) p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
} /* end case */
break;
+ case H5R_EXT_ATTR:
case H5R_ATTR:
{
- const hattr_ref_t *ref = (const hattr_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- const uint8_t *p; /* Pointer to OID to store */
size_t attr_name_len; /* Length of the attribute name */
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ if (!p) p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
/* Get the attribute name length */
@@ -748,7 +1035,7 @@ H5R_dereference(H5F_t *file, hid_t oapl_id, hid_t dxpl_id, H5R_type_t ref_type,
loc.path = &path;
/* Open an attribute */
- if(H5R_ATTR == ref_type) {
+ if(H5R_ATTR == ref->ref_type || H5R_EXT_ATTR == ref->ref_type) {
H5A_t *attr; /* Attribute opened */
/* Open the attribute */
@@ -828,10 +1115,11 @@ H5R_dereference(H5F_t *file, hid_t oapl_id, hid_t dxpl_id, H5R_type_t ref_type,
} /* end else */
done:
+ H5MM_xfree(filename);
H5MM_xfree(attr_name);
FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5R_dereference() */
+} /* end H5R__dereference() */
/*--------------------------------------------------------------------------
@@ -840,66 +1128,55 @@ done:
PURPOSE
Opens the HDF5 object referenced.
USAGE
- hid_t H5Rdereference2(ref)
- hid_t id; IN: Dataset reference object is in or location ID of
+ hid_t H5Rdereference2(obj_id, oapl_id, ref)
+ hid_t obj_id; IN: Dataset reference object is in or location ID of
object that the dataset is located within.
hid_t oapl_id; IN: Property list of the object being referenced.
- H5R_type_t ref_type; IN: Type of reference to create
- void *ref; IN: Reference to open.
+ href_t *ref; IN: Reference to open.
RETURNS
Valid ID on success, Negative on failure
DESCRIPTION
Given a reference to some object, open that object and return an ID for
that object.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
- Raymond Lu
- 13 July 2011
- I added the OAPL_ID parameter for the object being referenced. It only
- supports dataset access property list currently.
--------------------------------------------------------------------------*/
hid_t
-H5Rdereference2(hid_t obj_id, hid_t oapl_id, H5R_type_t ref_type, const void *_ref)
+H5Rdereference2(hid_t obj_id, hid_t oapl_id, const href_t *ref)
{
H5G_loc_t loc; /* Group location */
hid_t ret_value;
FUNC_ENTER_API(FAIL)
- H5TRACE4("i", "iiRt*x", obj_id, oapl_id, ref_type, _ref);
/* Check args */
if(H5G_loc(obj_id, &loc) < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
if(oapl_id < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a property list")
- if(ref_type <= H5R_BADTYPE || ref_type >= H5R_MAXTYPE)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
- if(_ref == NULL)
+ if(ref == NULL)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(ref->ref_type <= H5R_BADTYPE || ref->ref_type >= H5R_MAXTYPE)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
/* Create reference */
- if((ret_value = H5R_dereference(loc.oloc->file, oapl_id, H5AC_ind_dxpl_id, ref_type, _ref, TRUE)) < 0)
+ if((ret_value = H5R__dereference(loc.oloc->file, oapl_id, H5AC_ind_dxpl_id, ref, TRUE)) < 0)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to dereference object")
done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rdereference2() */
+} /* end H5Rdereference2() */
/*--------------------------------------------------------------------------
NAME
- H5R_get_region
+ H5R__get_region
PURPOSE
Retrieves a dataspace with the region pointed to selected.
USAGE
- H5S_t *H5R_get_region(file, dxpl_id, ref_type, ref)
+ H5S_t *H5R__get_region(file, dxpl_id, ref_type, ref)
H5F_t *file; IN: File the object being dereferenced is within
hid_t dxpl_id; IN: Property list ID
- H5R_type_t ref_type; IN: Type of reference to get region of
- void *ref; IN: Reference to open.
+ href_t *ref; IN: Reference to open.
RETURNS
Pointer to the dataspace on success, NULL on failure
@@ -907,46 +1184,43 @@ done:
Given a reference to some object, creates a copy of the dataset pointed
to's dataspace and defines a selection in the copy which is the region
pointed to.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
--------------------------------------------------------------------------*/
static H5S_t *
-H5R_get_region(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type, const void *_ref)
+H5R__get_region(H5F_t *file, hid_t dxpl_id, const href_t *ref)
{
H5O_loc_t oloc; /* Object location */
const uint8_t *p; /* Pointer to OID to store */
- H5HG_t hobjid; /* Heap object ID */
- uint8_t *buf = NULL; /* Buffer to store serialized selection in */
+ char *filename = NULL; /* Name of the file (for external references) */
H5S_t *ret_value;
FUNC_ENTER_NOAPI_NOINIT
- HDassert(_ref);
HDassert(file);
+ HDassert(ref);
+ HDassert((ref->ref_type == H5R_REGION) || (ref->ref_type == H5R_EXT_REGION));
/* Initialize the object location */
H5O_loc_reset(&oloc);
oloc.file = file;
- if (ref_type == H5R_DATASET_REGION) {
- /* Get the heap ID for the dataset region */
- p = (const uint8_t *)_ref;
- H5F_addr_decode(oloc.file, &p, &(hobjid.addr));
- UINT32DECODE(p, hobjid.idx);
+ /* Point to reference buffer now */
+ p = (const uint8_t *)ref->obj_enc.buf;
- /* Get the dataset region from the heap (allocate inside routine) */
- if((buf = (uint8_t *)H5HG_read(oloc.file, dxpl_id, &hobjid, NULL, NULL)) == NULL)
- HGOTO_ERROR(H5E_REFERENCE, H5E_READERROR, NULL, "Unable to read dataset region information")
+ if (ref->ref_type == H5R_EXT_REGION) {
+ size_t filename_len; /* Length of the file name */
- /* Point to heap buffer now */
- p = buf;
- } else {
- const hreg_ref_t *ref = (const hreg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
+ /* Get the file name length */
+ UINT16DECODE(p, filename_len);
+ HDassert(filename_len < H5R_MAX_ATTR_REF_NAME_LEN);
- /* Point to reference buffer now */
- p = (const uint8_t *)ref->buf;
+ /* Allocate space for the file name */
+ if(NULL == (filename = (char *)H5MM_malloc(filename_len + 1)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, NULL, "memory allocation failed")
+
+ /* Get the file name */
+ HDmemcpy(filename, p, filename_len);
+ filename[filename_len] = '\0';
+ p += filename_len;
}
/* Get the object oid for the dataset */
@@ -961,11 +1235,9 @@ H5R_get_region(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type, const void *_ref
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTDECODE, NULL, "can't deserialize selection")
done:
- /* Free the buffer allocated in H5HG_read() */
- H5MM_free(buf);
-
+ H5MM_xfree(filename);
FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5R_get_region() */
+} /* end H5R__get_region() */
/*--------------------------------------------------------------------------
@@ -974,11 +1246,10 @@ done:
PURPOSE
Retrieves a dataspace with the region pointed to selected.
USAGE
- hid_t H5Rget_region(id, ref_type, ref)
- hid_t id; IN: Dataset reference object is in or location ID of
+ hid_t H5Rget_region(loc_id, ref)
+ hid_t loc_id; IN: Dataset reference object is in or location ID of
object that the dataset is located within.
- H5R_type_t ref_type; IN: Type of reference to get region of
- void *ref; IN: Reference to open.
+ href_t *ref; IN: Reference to open.
RETURNS
Valid ID on success, Negative on failure
@@ -986,31 +1257,26 @@ done:
Given a reference to some object, creates a copy of the dataset pointed
to's dataspace and defines a selection in the copy which is the region
pointed to.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
--------------------------------------------------------------------------*/
hid_t
-H5Rget_region(hid_t id, H5R_type_t ref_type, const void *ref)
+H5Rget_region(hid_t loc_id, const href_t *ref)
{
H5G_loc_t loc; /* Object's group location */
H5S_t *space = NULL; /* Dataspace object */
hid_t ret_value;
FUNC_ENTER_API(FAIL)
- H5TRACE3("i", "iRt*x", id, ref_type, ref);
/* Check args */
- if(H5G_loc(id, &loc) < 0)
+ if(H5G_loc(loc_id, &loc) < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(ref_type != H5R_DATASET_REGION && ref_type != H5R_REGION)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
if(ref == NULL)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(ref->ref_type != H5R_REGION && ref->ref_type != H5R_EXT_REGION)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
/* Get the dataspace with the correct region selected */
- if((space = H5R_get_region(loc.oloc->file, H5AC_ind_dxpl_id, ref_type, ref)) == NULL)
+ if((space = H5R__get_region(loc.oloc->file, H5AC_ind_dxpl_id, ref)) == NULL)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTCREATE, FAIL, "unable to create dataspace")
/* Atomize */
@@ -1019,85 +1285,55 @@ H5Rget_region(hid_t id, H5R_type_t ref_type, const void *ref)
done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rget_region() */
+} /* end H5Rget_region() */
/*--------------------------------------------------------------------------
NAME
- H5R_get_obj_type
+ H5R__get_obj_type
PURPOSE
Retrieves the type of object that an object reference points to
USAGE
- H5O_type_t H5R_get_obj_type(file, ref_type, ref)
- H5F_t *file; IN: File the object being dereferenced is within
- H5R_type_t ref_type; IN: Type of reference to query
- void *ref; IN: Reference to query.
+ herr_t H5R_get_obj_type(file, dxpl_id, ref, obj_type)
+ H5F_t *file; IN: File the object being dereferenced is within
+ hid_t dxpl_id; IN: Property list ID
+ href_t *ref; IN: Reference to open
+ H5O_type_t *obj_type OUT: Object type
RETURNS
- Success: An object type defined in H5Gpublic.h
- Failure: H5G_UNKNOWN
+ Non-negative on success/Negative on failure
DESCRIPTION
Given a reference to some object, this function returns the type of object
pointed to.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
--------------------------------------------------------------------------*/
herr_t
-H5R_get_obj_type(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type,
- const void *_ref, H5O_type_t *obj_type)
+H5R__get_obj_type(H5F_t *file, hid_t dxpl_id, const href_t *ref, H5O_type_t *obj_type)
{
H5O_loc_t oloc; /* Object location */
- unsigned rc; /* Reference count of object */
+ unsigned rc; /* Reference count of object */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI_NOINIT
+ HDassert(ref);
HDassert(file);
- HDassert(_ref);
/* Initialize the symbol table entry */
H5O_loc_reset(&oloc);
oloc.file = file;
- switch(ref_type) {
+ switch(ref->ref_type) {
case H5R_OBJECT:
/* Get the object oid */
- oloc.addr = *(const hobj_ref_t *)_ref; /* Only object references currently supported */
+ oloc.addr = ref->obj_addr;
break;
- case H5R_DATASET_REGION:
- {
- H5HG_t hobjid; /* Heap object ID */
- const uint8_t *p; /* Pointer to reference to decode */
- uint8_t *buf; /* Buffer to store serialized selection in */
-
- /* Get the heap ID for the dataset region */
- p = (const uint8_t *)_ref;
- H5F_addr_decode(oloc.file, &p, &(hobjid.addr));
- UINT32DECODE(p, hobjid.idx);
-
- /* Get the dataset region from the heap (allocate inside routine) */
- if((buf = (uint8_t *)H5HG_read(oloc.file, dxpl_id, &hobjid, NULL, NULL)) == NULL)
- HGOTO_ERROR(H5E_REFERENCE, H5E_READERROR, FAIL, "Unable to read dataset region information")
-
- /* Get the object oid for the dataset */
- p = buf;
- H5F_addr_decode(oloc.file, &p, &(oloc.addr));
-
- /* Free the buffer allocated in H5HG_read() */
- H5MM_xfree(buf);
- break;
- } /* end case */
-
case H5R_REGION:
{
- const hreg_ref_t *ref = (const hreg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
const uint8_t *p; /* Pointer to reference to decode */
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
break;
@@ -1105,11 +1341,10 @@ H5R_get_obj_type(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type,
case H5R_ATTR:
{
- const hattr_ref_t *ref = (const hattr_ref_t *)_ref; /* Get pointer to correct type of reference struct */
const uint8_t *p; /* Pointer to reference to decode */
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
break;
@@ -1129,7 +1364,7 @@ H5R_get_obj_type(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type,
done:
FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5R_get_obj_type() */
+} /* end H5R__get_obj_type() */
/*--------------------------------------------------------------------------
@@ -1138,11 +1373,10 @@ done:
PURPOSE
Retrieves the type of object that an object reference points to
USAGE
- herr_t H5Rget_obj_type2(id, ref_type, ref, obj_type)
- hid_t id; IN: Dataset reference object is in or location ID of
+ herr_t H5Rget_obj_type2(loc_id, ref, obj_type)
+ hid_t loc_id; IN: Dataset reference object is in or location ID of
object that the dataset is located within.
- H5R_type_t ref_type; IN: Type of reference to query
- void *ref; IN: Reference to query.
+ href_t *ref; IN: Reference to query.
H5O_type_t *obj_type; OUT: Type of object reference points to
RETURNS
@@ -1150,52 +1384,45 @@ done:
DESCRIPTION
Given a reference to some object, this function retrieves the type of
object pointed to.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- EXAMPLES
- REVISION LOG
--------------------------------------------------------------------------*/
herr_t
-H5Rget_obj_type2(hid_t id, H5R_type_t ref_type, const void *ref,
- H5O_type_t *obj_type)
+H5Rget_obj_type2(hid_t loc_id, const href_t *ref, H5O_type_t *obj_type)
{
H5G_loc_t loc; /* Object location */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_API(FAIL)
- H5TRACE4("e", "iRt*x*Ot", id, ref_type, ref, obj_type);
/* Check args */
- if(H5G_loc(id, &loc) < 0)
+ if(H5G_loc(loc_id, &loc) < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(ref_type <= H5R_BADTYPE || ref_type >= H5R_MAXTYPE)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
if(ref == NULL)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(ref->ref_type <= H5R_BADTYPE || ref->ref_type >= H5R_MAXTYPE)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
/* Get the object information */
- if(H5R_get_obj_type(loc.oloc->file, H5AC_ind_dxpl_id, ref_type, ref, obj_type) < 0)
- HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to determine object type")
+ if(H5R__get_obj_type(loc.oloc->file, H5AC_ind_dxpl_id, ref, obj_type) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to determine object type")
done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rget_obj_type2() */
+} /* end H5Rget_obj_type2() */
/*--------------------------------------------------------------------------
NAME
- H5R_get_name
+ H5R__get_name
PURPOSE
Internal routine to determine a name for the object referenced
USAGE
- ssize_t H5R_get_name(f, dxpl_id, ref_type, ref, name, size)
+ ssize_t H5R__get_name(f, lapl_id, dxpl_id, loc_id, ref, name, size)
H5F_t *f; IN: Pointer to the file that the reference is pointing
into
hid_t lapl_id; IN: LAPL to use for operation
hid_t dxpl_id; IN: DXPL to use for operation
- hid_t id; IN: Location ID given for reference
- H5R_type_t ref_type; IN: Type of reference
- void *ref; IN: Reference to query.
+ hid_t loc_id; IN: Location ID given for reference
+ href_t *ref; IN: Reference to query.
char *name; OUT: Buffer to place name of object referenced
size_t size; IN: Size of name buffer
@@ -1204,81 +1431,83 @@ done:
DESCRIPTION
Given a reference to some object, determine a path to the object
referenced in the file.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- This may not be the only path to that object.
- EXAMPLES
- REVISION LOG
--------------------------------------------------------------------------*/
static ssize_t
-H5R_get_name(H5F_t *f, hid_t lapl_id, hid_t dxpl_id, hid_t id, H5R_type_t ref_type,
- const void *_ref, char *name, size_t size)
+H5R__get_name(H5F_t *f, hid_t lapl_id, hid_t dxpl_id, hid_t loc_id, const href_t *ref,
+ char *name, size_t size)
{
- hid_t file_id = H5I_INVALID_HID; /* ID for file that the reference is in */
+ hid_t file_id = H5I_BADID; /* ID for file that the reference is in */
H5O_loc_t oloc; /* Object location describing object for reference */
ssize_t ret_value = -1; /* Return value */
+ char *filename = NULL; /* Name of the file (for external references) */
+ const uint8_t *p; /* Pointer to reference to decode */
FUNC_ENTER_NOAPI_NOINIT
/* Check args */
HDassert(f);
- HDassert(_ref);
+ HDassert(ref);
/* Initialize the object location */
H5O_loc_reset(&oloc);
oloc.file = f;
- /* Get address for reference */
- switch(ref_type) {
- case H5R_OBJECT:
- oloc.addr = *(const hobj_ref_t *)_ref;
- break;
-
- case H5R_DATASET_REGION:
+ switch (ref->ref_type) {
+ case H5R_EXT_OBJECT:
+ case H5R_EXT_REGION:
+ case H5R_EXT_ATTR:
{
- H5HG_t hobjid; /* Heap object ID */
- uint8_t *buf; /* Buffer to store serialized selection in */
- const uint8_t *p; /* Pointer to OID to store */
+ size_t filename_len; /* Length of the file name */
- /* Get the heap ID for the dataset region */
- p = (const uint8_t *)_ref;
- H5F_addr_decode(oloc.file, &p, &(hobjid.addr));
- UINT32DECODE(p, hobjid.idx);
+ /* Get the file name length */
+ p = (const uint8_t *)ref->obj_enc.buf;
+ UINT16DECODE(p, filename_len);
+ HDassert(filename_len < H5R_MAX_ATTR_REF_NAME_LEN);
- /* Get the dataset region from the heap (allocate inside routine) */
- if((buf = (uint8_t *)H5HG_read(oloc.file, dxpl_id, &hobjid, NULL, NULL)) == NULL)
- HGOTO_ERROR(H5E_REFERENCE, H5E_READERROR, FAIL, "Unable to read dataset region information")
+ /* Allocate space for the file name */
+ if(NULL == (filename = (char *)H5MM_malloc(filename_len + 1)))
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTALLOC, FAIL, "memory allocation failed")
- /* Get the object oid for the dataset */
- p = buf;
- H5F_addr_decode(oloc.file, &p, &(oloc.addr));
+ /* Get the file name */
+ HDmemcpy(filename, p, filename_len);
+ filename[filename_len] = '\0';
+ p += filename_len;
+ }
+ break;
+ case H5R_OBJECT:
+ case H5R_REGION:
+ case H5R_ATTR:
+ case H5R_BADTYPE:
+ case H5R_MAXTYPE:
+ default:
+ break;
+ }
- /* Free the buffer allocated in H5HG_read() */
- H5MM_xfree(buf);
- } /* end case */
- break;
+ /* Get address for reference */
+ switch(ref->ref_type) {
+ case H5R_OBJECT:
+ oloc.addr = ref->obj_addr;
+ break;
+ case H5R_EXT_OBJECT:
+ case H5R_EXT_REGION:
case H5R_REGION:
{
- const hreg_ref_t *ref = (const hreg_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- const uint8_t *p; /* Pointer to reference to decode */
-
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ if (!p) p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
} /* end case */
break;
+ case H5R_EXT_ATTR:
case H5R_ATTR:
{
- const hattr_ref_t *ref = (const hattr_ref_t *)_ref; /* Get pointer to correct type of reference struct */
- const uint8_t *p; /* Pointer to OID to store */
size_t attr_name_len; /* Length of the attribute name */
size_t copy_len;
/* Get the object oid for the dataset */
- p = (const uint8_t *)ref->buf;
+ if (!p) p = (const uint8_t *)ref->obj_enc.buf;
H5F_addr_decode(oloc.file, &p, &(oloc.addr));
/* Get the attribute name length */
@@ -1301,9 +1530,9 @@ H5R_get_name(H5F_t *f, hid_t lapl_id, hid_t dxpl_id, hid_t id, H5R_type_t ref_ty
HGOTO_ERROR(H5E_REFERENCE, H5E_UNSUPPORTED, FAIL, "internal error (unknown reference type)")
} /* end switch */
- if (ref_type != H5R_ATTR) {
+ if (ref->ref_type != H5R_ATTR && ref->ref_type != H5R_EXT_ATTR) {
/* Retrieve file ID for name search */
- if((file_id = H5I_get_file_id(id, FALSE)) < 0)
+ if((file_id = H5I_get_file_id(loc_id, FALSE)) < 0)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTGET, FAIL, "can't retrieve file ID")
/* Get name, length, etc. */
@@ -1315,9 +1544,9 @@ done:
/* Close file ID used for search */
if(file_id > 0 && H5I_dec_ref(file_id) < 0)
HDONE_ERROR(H5E_REFERENCE, H5E_CANTDEC, FAIL, "can't decrement ref count of temp ID")
-
+ H5MM_xfree(filename);
FUNC_LEAVE_NOAPI(ret_value)
-} /* end H5R_get_name() */
+} /* end H5R__get_name() */
/*--------------------------------------------------------------------------
@@ -1326,11 +1555,10 @@ done:
PURPOSE
Determines a name for the object referenced
USAGE
- ssize_t H5Rget_name(loc_id, ref_type, ref, name, size)
+ ssize_t H5Rget_name(loc_id, ref, name, size)
hid_t loc_id; IN: Dataset reference object is in or location ID of
object that the dataset is located within.
- H5R_type_t ref_type; IN: Type of reference
- void *ref; IN: Reference to query.
+ href_t *ref; IN: Reference to query.
char *name; OUT: Buffer to place name of object referenced. If NULL
then this call will return the size in bytes of name.
size_t size; IN: Size of name buffer (user needs to include NULL terminator
@@ -1341,45 +1569,137 @@ done:
DESCRIPTION
Given a reference to some object, determine a path to the object
referenced in the file.
- GLOBAL VARIABLES
- COMMENTS, BUGS, ASSUMPTIONS
- This may not be the only path to that object.
- EXAMPLES
- REVISION LOG
- M. Scot Breitenfeld
- 22 January 2014
- Changed the behavior for the returned value of the function when name is NULL.
- If name is NULL then size is ignored and the function returns the size
- of the name buffer (not including the NULL terminator), it still returns
- negative on failure.
--------------------------------------------------------------------------*/
ssize_t
-H5Rget_name(hid_t id, H5R_type_t ref_type, const void *_ref, char *name,
- size_t size)
+H5Rget_name(hid_t loc_id, const href_t *ref, char *name, size_t size)
{
H5G_loc_t loc; /* Group location */
H5F_t *file; /* File object */
ssize_t ret_value; /* Return value */
FUNC_ENTER_API(FAIL)
- H5TRACE5("Zs", "iRt*x*sz", id, ref_type, _ref, name, size);
/* Check args */
- if(H5G_loc(id, &loc) < 0)
+ if(H5G_loc(loc_id, &loc) < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
- if(ref_type <= H5R_BADTYPE || ref_type >= H5R_MAXTYPE)
- HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
- if(_ref == NULL)
+ if(ref == NULL)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(ref->ref_type <= H5R_BADTYPE || ref->ref_type >= H5R_MAXTYPE)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
/* Get the file pointer from the entry */
file = loc.oloc->file;
/* Get name */
- if((ret_value = H5R_get_name(file, H5P_DEFAULT, H5AC_ind_dxpl_id, id, ref_type, _ref, name, size)) < 0)
+ if((ret_value = H5R__get_name(file, H5P_DEFAULT, H5AC_ind_dxpl_id, loc_id, ref, name, size)) < 0)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to determine object path")
done:
FUNC_LEAVE_API(ret_value)
} /* end H5Rget_name() */
+/*--------------------------------------------------------------------------
+ NAME
+ H5R__get_filename
+ PURPOSE
+ Determines a file name for the object referenced
+ USAGE
+ ssize_t H5R__get_filename(ref, name, size)
+ href_t *ref; IN: Reference to query.
+ char *name; OUT: Buffer to place file name of object referenced. If NULL
+ then this call will return the size in bytes of name.
+ size_t size; IN: Size of name buffer (user needs to include NULL terminator
+ when passing in the size)
+
+ RETURNS
+ Non-negative length of the path on success, Negative on failure
+ DESCRIPTION
+ Given a reference to some object, determine a file name to the object
+ referenced.
+--------------------------------------------------------------------------*/
+static ssize_t
+H5R__get_filename(const href_t *ref, char *name, size_t size)
+{
+ ssize_t ret_value = -1; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT
+
+ /* Check args */
+ HDassert(ref);
+
+ switch (ref->ref_type) {
+ case H5R_EXT_OBJECT:
+ case H5R_EXT_REGION:
+ case H5R_EXT_ATTR:
+ {
+ const uint8_t *p; /* Pointer to reference to decode */
+ size_t filename_len; /* Length of the file name */
+ size_t copy_len;
+
+ /* Get the file name length */
+ p = (const uint8_t *)ref->obj_enc.buf;
+ UINT16DECODE(p, filename_len);
+ copy_len = MIN(filename_len, size - 1);
+
+ /* Get the attribute name */
+ if (name) {
+ HDmemcpy(name, p, copy_len);
+ name[copy_len] = '\0';
+ }
+ ret_value = (ssize_t)copy_len;
+ }
+ break;
+ case H5R_OBJECT:
+ case H5R_REGION:
+ case H5R_ATTR:
+ case H5R_BADTYPE:
+ case H5R_MAXTYPE:
+ default:
+ HDassert("unknown reference type" && 0);
+ HGOTO_ERROR(H5E_REFERENCE, H5E_UNSUPPORTED, FAIL, "internal error (unknown reference type)")
+ break;
+ } /* end switch */
+
+done:
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5R__get_filename() */
+
+/*--------------------------------------------------------------------------
+ NAME
+ H5Rget_filename
+ PURPOSE
+ Determines a file name for the object referenced
+ USAGE
+ ssize_t H5Rget_filename(ref, name, size)
+ href_t *ref; IN: Reference to query.
+ char *name; OUT: Buffer to place file name of object referenced. If NULL
+ then this call will return the size in bytes of name.
+ size_t size; IN: Size of name buffer (user needs to include NULL terminator
+ when passing in the size)
+
+ RETURNS
+ Non-negative length of the path on success, Negative on failure
+ DESCRIPTION
+ Given a reference to some object, determine a file name to the object
+ referenced.
+--------------------------------------------------------------------------*/
+ssize_t
+H5Rget_filename(const href_t *ref, char *name, size_t size)
+{
+ ssize_t ret_value; /* Return value */
+
+ FUNC_ENTER_API(FAIL)
+
+ /* Check args */
+ if(ref == NULL)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
+ if(ref->ref_type <= H5R_BADTYPE || ref->ref_type >= H5R_MAXTYPE)
+ HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
+
+ /* Get name */
+ if((ret_value = H5R__get_filename(ref, name, size)) < 0)
+ HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable to retrieve file name")
+
+done:
+ FUNC_LEAVE_API(ret_value)
+} /* end H5Rget_filename() */
diff --git a/src/H5Rdeprec.c b/src/H5Rdeprec.c
index b8133b2..05cfb71 100644
--- a/src/H5Rdeprec.c
+++ b/src/H5Rdeprec.c
@@ -125,7 +125,7 @@ H5Rget_obj_type1(hid_t id, H5R_type_t ref_type, const void *ref)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, H5G_UNKNOWN, "invalid reference pointer")
/* Get the object information */
- if(H5R_get_obj_type(loc.oloc->file, H5AC_ind_dxpl_id, ref_type, ref, &obj_type) < 0)
+ if(H5R__get_obj_type(loc.oloc->file, H5AC_ind_dxpl_id, ref, &obj_type) < 0)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, H5G_UNKNOWN, "unable to determine object type")
/* Set return value */
@@ -133,7 +133,7 @@ H5Rget_obj_type1(hid_t id, H5R_type_t ref_type, const void *ref)
done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rget_obj_type1() */
+} /* end H5Rget_obj_type1() */
/*--------------------------------------------------------------------------
@@ -159,7 +159,7 @@ done:
REVISION LOG
--------------------------------------------------------------------------*/
hid_t
-H5Rdereference1(hid_t obj_id, H5R_type_t ref_type, const void *_ref)
+H5Rdereference1(hid_t obj_id, H5R_type_t ref_type, const void *ref)
{
H5G_loc_t loc; /* Group location */
H5F_t *file = NULL; /* File object */
@@ -173,19 +173,19 @@ H5Rdereference1(hid_t obj_id, H5R_type_t ref_type, const void *_ref)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a location")
if(ref_type <= H5R_BADTYPE || ref_type >= H5R_MAXTYPE)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference type")
- if(_ref == NULL)
+ if(ref == NULL)
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid reference pointer")
/* Get the file pointer from the entry */
file = loc.oloc->file;
/* Create reference */
- if((ret_value = H5R_dereference(file, H5P_DATASET_ACCESS_DEFAULT, H5AC_ind_dxpl_id, ref_type, _ref, TRUE)) < 0)
+ if((ret_value = H5R__dereference(file, H5P_DATASET_ACCESS_DEFAULT, H5AC_ind_dxpl_id, ref, TRUE)) < 0)
HGOTO_ERROR(H5E_REFERENCE, H5E_CANTINIT, FAIL, "unable dereference object")
done:
FUNC_LEAVE_API(ret_value)
-} /* end H5Rdereference1() */
+} /* end H5Rdereference1() */
#endif /* H5_NO_DEPRECATED_SYMBOLS */
diff --git a/src/H5Rpkg.h b/src/H5Rpkg.h
index 8ed8d65..bc9d933 100644
--- a/src/H5Rpkg.h
+++ b/src/H5Rpkg.h
@@ -54,10 +54,10 @@
/******************************/
/* General functions */
-H5_DLL herr_t H5R_get_obj_type(H5F_t *file, hid_t dxpl_id, H5R_type_t ref_type,
- const void *_ref, H5O_type_t *obj_type);
-H5_DLL hid_t H5R_dereference(H5F_t *file, hid_t dapl_id, hid_t dxpl_id, H5R_type_t ref_type,
- const void *_ref, hbool_t app_ref);
+H5_DLL herr_t H5R__get_obj_type(H5F_t *file, hid_t dxpl_id, const href_t *ref,
+ H5O_type_t *obj_type);
+H5_DLL hid_t H5R__dereference(H5F_t *file, hid_t dapl_id, hid_t dxpl_id,
+ const href_t *ref, hbool_t app_ref);
#endif /* _H5Rpkg_H */
diff --git a/src/H5Rprivate.h b/src/H5Rprivate.h
index ba19c8b..bc51b21 100644
--- a/src/H5Rprivate.h
+++ b/src/H5Rprivate.h
@@ -26,9 +26,29 @@
#include "H5Gprivate.h"
/* Internal data structures */
+struct href_t {
+ H5R_type_t ref_type;
+ union {
+ struct {
+ size_t buf_size;/* Size of serialized reference */
+ void *buf; /* Pointer to serialized reference */
+ } obj_enc;
+ haddr_t obj_addr;
+ };
+};
+
+#define H5R_INITIALIZER { H5R_BADTYPE, {0, NULL} }
+
+/* To prevent including H5Sprivate.h that includes H5Rprivate.h */
+struct H5S_t;
/* Private functions */
-H5_DLL herr_t H5R_create(void *ref, H5R_type_t ref_type, ...);
+H5_DLL href_t *H5R_create_object(H5G_loc_t *loc, const char *name, hid_t dxpl_id);
+H5_DLL href_t *H5R_create_region(H5G_loc_t *loc, const char *name, hid_t dxpl_id, struct H5S_t *space);
+H5_DLL href_t *H5R_create_attr(H5G_loc_t *loc, const char *name, hid_t dxpl_id, const char *attr_name);
+H5_DLL href_t *H5R_create_ext_object(H5G_loc_t *loc, const char *name, hid_t dxpl_id);
+H5_DLL href_t *H5R_create_ext_region(H5G_loc_t *loc, const char *name, hid_t dxpl_id, struct H5S_t *space);
+H5_DLL href_t *H5R_create_ext_attr(H5G_loc_t *loc, const char *name, hid_t dxpl_id, const char *attr_name);
+H5_DLL herr_t H5R_destroy(href_t *ref);
#endif /* _H5Rprivate_H */
-
diff --git a/src/H5Rpublic.h b/src/H5Rpublic.h
index 580a5d3..f792202 100644
--- a/src/H5Rpublic.h
+++ b/src/H5Rpublic.h
@@ -30,43 +30,16 @@
typedef enum {
H5R_BADTYPE = (-1), /*invalid Reference Type */
H5R_OBJECT, /*Object reference */
- H5R_DATASET_REGION, /*Dataset Region Reference */
- H5R_REGION, /*Revised Dataset Region Reference */
+ H5R_REGION, /*Dataset Region Reference */
H5R_ATTR, /*Attribute Reference */
- H5R_MAXTYPE /*highest type (Invalid as true type) */
+ H5R_EXT_OBJECT, /*External Object reference */
+ H5R_EXT_REGION, /*External Region reference */
+ H5R_EXT_ATTR, /*External Attribute reference */
+ H5R_MAXTYPE /*highest type (Invalid as true type) */
} H5R_type_t;
-/* Note! Be careful with the sizes of the references because they should really
- * depend on the run-time values in the file. Unfortunately, the arrays need
- * to be defined at compile-time, so we have to go with the worst case sizes for
- * them. -QAK
- */
-#define H5R_OBJ_REF_BUF_SIZE sizeof(haddr_t)
-/* Object reference structure for user's code */
-typedef haddr_t hobj_ref_t; /* Needs to be large enough to store largest haddr_t in a worst case machine (ie. 8 bytes currently) */
-
-#define H5R_DSET_REG_REF_BUF_SIZE (sizeof(haddr_t)+4)
-/* 4 is used instead of sizeof(int) to permit portability between
- the Crays and other machines (the heap ID is always encoded as an int32 anyway)
-*/
-/* Dataset Region reference structure for user's code */
-typedef unsigned char hdset_reg_ref_t[H5R_DSET_REG_REF_BUF_SIZE];/* Buffer to store heap ID and index */
-/* Needs to be large enough to store largest haddr_t in a worst case machine (ie. 8 bytes currently) plus an int */
-
-/* Variable length reference struct in memory */
-struct href_var {
- size_t buf_size;/* Size of serialized reference */
- void *buf; /* Pointer to serialized reference */
-};
-
-typedef struct href_var hreg_ref_t;
-
-#define H5R_REG_REF_INITIALIZER { 0, NULL }
-
-/* Attribute reference structure for user's code (variable length) */
-typedef struct href_var hattr_ref_t;
-
-#define H5R_ATTR_REF_INITIALIZER { 0, NULL }
+/* Opaque reference type */
+typedef struct href_t href_t;
/* Publicly visible data structures */
@@ -75,13 +48,19 @@ extern "C" {
#endif
/* Functions in H5R.c */
-H5_DLL herr_t H5Rcreate(void *ref, H5R_type_t ref_type, ...);
-H5_DLL hid_t H5Rdereference2(hid_t obj_id, hid_t oapl_id, H5R_type_t ref_type, const void *ref);
-H5_DLL hid_t H5Rget_region(hid_t dataset, H5R_type_t ref_type, const void *ref);
-H5_DLL herr_t H5Rget_obj_type2(hid_t id, H5R_type_t ref_type, const void *_ref,
- H5O_type_t *obj_type);
-H5_DLL ssize_t H5Rget_name(hid_t loc_id, H5R_type_t ref_type, const void *ref,
- char *name/*out*/, size_t size);
+H5_DLL href_t *H5Rcreate_object(hid_t loc_id, const char *name);
+H5_DLL href_t *H5Rcreate_region(hid_t loc_id, const char *name, hid_t space_id);
+H5_DLL href_t *H5Rcreate_attr(hid_t loc_id, const char *name, const char *attr_name);
+H5_DLL href_t *H5Rcreate_ext_object(hid_t loc_id, const char *name);
+H5_DLL href_t *H5Rcreate_ext_region(hid_t loc_id, const char *name, hid_t space_id);
+H5_DLL href_t *H5Rcreate_ext_attr(hid_t loc_id, const char *name, const char *attr_name);
+H5_DLL herr_t H5Rdestroy(href_t *ref);
+
+H5_DLL hid_t H5Rdereference2(hid_t obj_id, hid_t oapl_id, const href_t *ref);
+H5_DLL hid_t H5Rget_region(hid_t loc_id, const href_t *ref);
+H5_DLL herr_t H5Rget_obj_type2(hid_t loc_id, const href_t *ref, H5O_type_t *obj_type);
+H5_DLL ssize_t H5Rget_name(hid_t loc_id, const href_t *ref, char *name/*out*/, size_t size);
+H5_DLL ssize_t H5Rget_filename(const href_t *ref, char *name/*out*/, size_t size);
/* Symbols defined for compatibility with previous versions of the HDF5 API.
*
@@ -96,6 +75,7 @@ H5_DLL ssize_t H5Rget_name(hid_t loc_id, H5R_type_t ref_type, const void *ref,
/* Function prototypes */
+/* TODO should add a H5Rcreate1 that maps to other types */
H5_DLL H5G_obj_t H5Rget_obj_type1(hid_t id, H5R_type_t ref_type, const void *_ref);
H5_DLL hid_t H5Rdereference1(hid_t obj_id, H5R_type_t ref_type, const void *ref);
diff --git a/src/H5T.c b/src/H5T.c
index 36c5745..fa4c390 100644
--- a/src/H5T.c
+++ b/src/H5T.c
@@ -218,32 +218,38 @@
#define H5T_INIT_TYPE_REF_COMMON { \
H5T_INIT_TYPE_ALLOC_COMMON(H5T_REFERENCE) \
H5T_INIT_TYPE_NUM_COMMON(H5T_ORDER_NONE) \
+ dt->shared->force_conv = TRUE; \
+ dt->shared->u.atomic.u.r.loc = H5T_LOC_BADLOC; \
}
#define H5T_INIT_TYPE_OBJREF_CORE { \
H5T_INIT_TYPE_REF_COMMON \
- dt->shared->force_conv = TRUE; \
dt->shared->u.atomic.u.r.rtype = H5R_OBJECT; \
- dt->shared->u.atomic.u.r.loc = H5T_LOC_MEMORY; \
}
-#define H5T_INIT_TYPE_DSET_REGREF_CORE { \
+#define H5T_INIT_TYPE_REGREF_CORE { \
H5T_INIT_TYPE_REF_COMMON \
- dt->shared->u.atomic.u.r.rtype = H5R_DATASET_REGION; \
+ dt->shared->u.atomic.u.r.rtype = H5R_REGION; \
}
-#define H5T_INIT_TYPE_REGREF_CORE { \
- H5T_INIT_TYPE_REF_COMMON \
- dt->shared->force_conv = TRUE; \
- dt->shared->u.atomic.u.r.rtype = H5R_REGION; \
- dt->shared->u.atomic.u.r.loc = H5T_LOC_BADLOC; \
+#define H5T_INIT_TYPE_ATTRREF_CORE { \
+ H5T_INIT_TYPE_REF_COMMON \
+ dt->shared->u.atomic.u.r.rtype = H5R_ATTR; \
}
-#define H5T_INIT_TYPE_ATTRREF_CORE { \
- H5T_INIT_TYPE_REF_COMMON \
- dt->shared->force_conv = TRUE; \
- dt->shared->u.atomic.u.r.rtype = H5R_ATTR; \
- dt->shared->u.atomic.u.r.loc = H5T_LOC_BADLOC; \
+#define H5T_INIT_TYPE_EXTOBJREF_CORE { \
+ H5T_INIT_TYPE_REF_COMMON \
+ dt->shared->u.atomic.u.r.rtype = H5R_EXT_OBJECT; \
+}
+
+#define H5T_INIT_TYPE_EXTREGREF_CORE { \
+ H5T_INIT_TYPE_REF_COMMON \
+ dt->shared->u.atomic.u.r.rtype = H5R_EXT_REGION; \
+}
+
+#define H5T_INIT_TYPE_EXTATTRREF_CORE { \
+ H5T_INIT_TYPE_REF_COMMON \
+ dt->shared->u.atomic.u.r.rtype = H5R_EXT_ATTR; \
}
/* Define the code templates for the "SIZE_TMPL" in the H5T_INIT_TYPE macro */
@@ -356,10 +362,12 @@ hid_t H5T_STD_B32BE_g = FAIL;
hid_t H5T_STD_B32LE_g = FAIL;
hid_t H5T_STD_B64BE_g = FAIL;
hid_t H5T_STD_B64LE_g = FAIL;
-hid_t H5T_STD_REF_OBJ_g = FAIL;
-hid_t H5T_STD_REF_DSETREG_g = FAIL;
-hid_t H5T_STD_REF_REG_g = FAIL;
-hid_t H5T_STD_REF_ATTR_g = FAIL;
+hid_t H5T_STD_REF_OBJ_g = FAIL;
+hid_t H5T_STD_REF_REG_g = FAIL;
+hid_t H5T_STD_REF_ATTR_g = FAIL;
+hid_t H5T_STD_REF_EXT_OBJ_g = FAIL;
+hid_t H5T_STD_REF_EXT_REG_g = FAIL;
+hid_t H5T_STD_REF_EXT_ATTR_g = FAIL;
hid_t H5T_UNIX_D32BE_g = FAIL;
hid_t H5T_UNIX_D32LE_g = FAIL;
@@ -448,10 +456,7 @@ size_t H5T_NATIVE_LDOUBLE_COMP_ALIGN_g = 0;
size_t H5T_POINTER_COMP_ALIGN_g = 0;
size_t H5T_HVL_COMP_ALIGN_g = 0;
-size_t H5T_HOBJREF_COMP_ALIGN_g = 0;
-size_t H5T_HDSETREGREF_COMP_ALIGN_g = 0;
-size_t H5T_HREGREF_COMP_ALIGN_g = 0;
-size_t H5T_HATTRREF_COMP_ALIGN_g = 0;
+size_t H5T_HREF_COMP_ALIGN_g = 0;
/*
* Alignment constraints for native types. These are initialized at run time
@@ -739,6 +744,9 @@ H5T__init_package(void)
H5T_t *objref=NULL; /* Datatype structure for object reference objects */
H5T_t *regref=NULL; /* Datatype structure for region reference objects */
H5T_t *attrref=NULL; /* Datatype structure for attribute reference objects */
+ H5T_t *extobjref=NULL; /* Datatype structure for external object reference objects */
+ H5T_t *extregref=NULL; /* Datatype structure for external region reference objects */
+ H5T_t *extattrref=NULL; /* Datatype structure for external attribute reference objects */
hsize_t dim[1]={1}; /* Dimension info for array datatype */
herr_t status;
unsigned copied_dtype=1; /* Flag to indicate whether datatype was copied or allocated (for error cleanup) */
@@ -991,26 +999,41 @@ H5T__init_package(void)
*/
/* Object reference (i.e. object header address in file) */
- H5T_INIT_TYPE(OBJREF, H5T_STD_REF_OBJ_g, ALLOC, -, SET, H5R_OBJ_REF_BUF_SIZE)
+ H5T_INIT_TYPE(OBJREF, H5T_STD_REF_OBJ_g, ALLOC, -, NOSET, -)
+ if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
objref = dt; /* Keep type for later */
/* Dataset Region reference (i.e. selection inside a dataset) */
- H5T_INIT_TYPE(DSET_REGREF, H5T_STD_REF_DSETREG_g, ALLOC, -, SET, H5R_DSET_REG_REF_BUF_SIZE)
-
- /* Dataset Region reference (i.e. selection inside a dataset) */
H5T_INIT_TYPE(REGREF, H5T_STD_REF_REG_g, ALLOC, -, NOSET, -)
- /* TODO put that in the macro */
if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
regref = dt; /* Keep type for later */
/* Attribute reference (i.e. object and attribute names in file) */
H5T_INIT_TYPE(ATTRREF, H5T_STD_REF_ATTR_g, ALLOC, -, NOSET, -)
- /* TODO put that in the macro */
if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
attrref = dt; /* Keep type for later */
+ /* Object reference (i.e. object header address in file) */
+ H5T_INIT_TYPE(EXTOBJREF, H5T_STD_REF_EXT_OBJ_g, ALLOC, -, NOSET, -)
+ if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
+ extobjref = dt; /* Keep type for later */
+
+ /* Dataset Region reference (i.e. selection inside a dataset) */
+ H5T_INIT_TYPE(EXTREGREF, H5T_STD_REF_EXT_REG_g, ALLOC, -, NOSET, -)
+ if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
+ extregref = dt; /* Keep type for later */
+
+ /* Attribute reference (i.e. object and attribute names in file) */
+ H5T_INIT_TYPE(EXTATTRREF, H5T_STD_REF_EXT_ATTR_g, ALLOC, -, NOSET, -)
+ if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location")
+ extattrref = dt; /* Keep type for later */
+
/*
* Register conversion functions beginning with the most general and
* ending with the most specific.
@@ -1044,7 +1067,7 @@ H5T__init_package(void)
status |= H5T_register(H5T_PERS_SOFT, "enum_f", enum_type, floatpt, H5T__conv_enum_numeric, H5AC_ind_dxpl_id, FALSE);
status |= H5T_register(H5T_PERS_SOFT, "vlen", vlen, vlen, H5T__conv_vlen, H5AC_ind_dxpl_id, FALSE);
status |= H5T_register(H5T_PERS_SOFT, "array", array, array, H5T__conv_array, H5AC_ind_dxpl_id, FALSE);
- status |= H5T_register(H5T_PERS_SOFT, "objref", objref, objref, H5T__conv_order_opt, H5AC_ind_dxpl_id, FALSE);
+ status |= H5T_register(H5T_PERS_SOFT, "objref", objref, objref, H5T__conv_ref, H5AC_ind_dxpl_id, FALSE);
status |= H5T_register(H5T_PERS_SOFT, "regref", regref, regref, H5T__conv_ref, H5AC_ind_dxpl_id, FALSE);
status |= H5T_register(H5T_PERS_SOFT, "attrref", attrref, attrref, H5T__conv_ref, H5AC_ind_dxpl_id, FALSE);
@@ -1475,8 +1498,7 @@ H5T_top_term_package(void)
H5T_STD_B32LE_g = FAIL;
H5T_STD_B64BE_g = FAIL;
H5T_STD_B64LE_g = FAIL;
- H5T_STD_REF_OBJ_g = FAIL;
- H5T_STD_REF_DSETREG_g = FAIL;
+ H5T_STD_REF_OBJ_g = FAIL;
H5T_STD_REF_REG_g = FAIL;
H5T_STD_REF_ATTR_g = FAIL;
@@ -4357,11 +4379,6 @@ H5T_cmp(const H5T_t *dt1, const H5T_t *dt2, hbool_t superset)
HGOTO_DONE(1);
break;
- case H5R_DATASET_REGION:
- /* Does this need more to distinguish it? -QAK 11/30/98 */
- /*void */
- break;
-
case H5R_REGION:
if (dt1->shared->u.atomic.u.r.loc < dt2->shared->u.atomic.u.r.loc)
HGOTO_DONE(-1);
@@ -4369,8 +4386,23 @@ H5T_cmp(const H5T_t *dt1, const H5T_t *dt2, hbool_t superset)
HGOTO_DONE(1);
break;
- case H5R_ATTR:
- /* Does this need more to distinguish it? -QAK 8/25/15 */
+ case H5R_ATTR:
+ /* Does this need more to distinguish it? -QAK 8/25/15 */
+ /*void */
+ break;
+
+ case H5R_EXT_OBJECT:
+ /* Does this need more to distinguish it? -QAK 8/25/15 */
+ /*void */
+ break;
+
+ case H5R_EXT_REGION:
+ /* Does this need more to distinguish it? -QAK 8/25/15 */
+ /*void */
+ break;
+
+ case H5R_EXT_ATTR:
+ /* Does this need more to distinguish it? -QAK 8/25/15 */
/*void */
break;
@@ -5288,25 +5320,11 @@ H5T_set_loc(H5T_t *dt, H5F_t *f, H5T_loc_t loc)
break;
case H5T_REFERENCE:
- /* Only need to change location of object references */
- if(dt->shared->u.atomic.u.r.rtype==H5R_OBJECT) {
- /* Mark this reference */
- if(loc!=dt->shared->u.atomic.u.r.loc) {
- /* Set the location */
- dt->shared->u.atomic.u.r.loc = loc;
-
- /* Indicate that the location changed */
- ret_value=TRUE;
- } /* end if */
- } /* end if */
- if((dt->shared->u.atomic.u.r.rtype == H5R_REGION) ||
- (dt->shared->u.atomic.u.r.rtype == H5R_ATTR)) {
- /* Mark this reference */
- if((changed = H5T__ref_set_loc(dt, f, loc)) < 0)
- HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "Unable to set reference location");
- if(changed > 0)
- ret_value = changed;
- }
+ /* Mark this reference */
+ if((changed = H5T__ref_set_loc(dt, f, loc)) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "Unable to set reference location");
+ if(changed > 0)
+ ret_value = changed;
break;
case H5T_NO_CLASS:
diff --git a/src/H5Tconv.c b/src/H5Tconv.c
index 534ab99..4f6d02f 100644
--- a/src/H5Tconv.c
+++ b/src/H5Tconv.c
@@ -3584,6 +3584,7 @@ H5T__conv_ref(hid_t src_id, hid_t dst_id, H5T_cdata_t *cdata, size_t nelmts,
uint8_t *b = NULL; /* background buffer */
ssize_t s_stride, d_stride; /* src and dst strides */
ssize_t b_stride; /* bkg stride */
+ size_t safe; /* how many elements are safe to process in each pass */
void *conv_buf = NULL; /* temporary conversion buffer */
size_t conv_buf_size = 0; /* size of conversion buffer in bytes */
size_t elmtno; /* element number counter */
@@ -3616,13 +3617,16 @@ H5T__conv_ref(hid_t src_id, hid_t dst_id, H5T_cdata_t *cdata, size_t nelmts,
case H5T_CONV_CONV:
{
+ H5R_type_t ref_type;
+
/*
* Conversion.
*/
if(NULL == (src = (H5T_t *)H5I_object(src_id)) || NULL == (dst = (H5T_t *)H5I_object(dst_id)))
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a datatype")
- if (src->shared->u.atomic.u.r.rtype == H5R_OBJECT) break;
+ /* Set reference type */
+ ref_type = src->shared->u.atomic.u.r.rtype;
/* Initialize source & destination strides */
if(buf_stride) {
@@ -3646,36 +3650,78 @@ H5T__conv_ref(hid_t src_id, hid_t dst_id, H5T_cdata_t *cdata, size_t nelmts,
else
b_stride = 0;
- /* Single forward pass over all data */
- s = d = (uint8_t *)buf;
- b = (uint8_t *)bkg;
+ /* The outer loop of the type conversion macro, controlling which */
+ /* direction the buffer is walked */
+ while(nelmts > 0) {
+ /* Check if we need to go backwards through the buffer */
+ if(d_stride > s_stride) {
+ /* Sanity check */
+ HDassert(s_stride > 0);
+ HDassert(d_stride > 0);
+ HDassert(b_stride >= 0);
- for(elmtno = 0; elmtno < nelmts; elmtno++) {
- size_t buf_size;
+ /* Compute the number of "safe" destination elements at */
+ /* the end of the buffer (Those which don't overlap with */
+ /* any source elements at the beginning of the buffer) */
+ safe = nelmts - (((nelmts * (size_t)s_stride) + ((size_t)d_stride - 1)) / (size_t)d_stride);
- /* Get size of references */
- if(0 == (buf_size = (*(src->shared->u.atomic.u.r.getsize))(s)))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "incorrect length")
+ /* If we're down to the last few elements, just wrap up */
+ /* with a "real" reverse copy */
+ if(safe < 2) {
+ s = (uint8_t *)buf + (nelmts - 1) * (size_t)s_stride;
+ d = (uint8_t *)buf + (nelmts - 1) * (size_t)d_stride;
+ b = (uint8_t *)bkg + (nelmts - 1) * (size_t)b_stride;
+ s_stride = -s_stride;
+ d_stride = -d_stride;
+ b_stride = -b_stride;
- /* Check if conversion buffer is large enough, resize if necessary. */
- conv_buf_size = buf_size;
- if(NULL == (conv_buf = H5FL_BLK_REALLOC(ref_seq, conv_buf, conv_buf_size)))
- HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed for type conversion")
- HDmemset(conv_buf, 0, conv_buf_size);
+ safe = nelmts;
+ } /* end if */
+ else {
+ s = (uint8_t *)buf + (nelmts - safe) * (size_t)s_stride;
+ d = (uint8_t *)buf + (nelmts - safe) * (size_t)d_stride;
+ b = (uint8_t *)bkg + (nelmts - safe) * (size_t)b_stride;
+ } /* end else */
+ } /* end if */
+ else {
+ /* Single forward pass over all data */
+ s = d = (uint8_t *)buf;
+ b = (uint8_t *)bkg;
+ safe = nelmts;
+ } /* end else */
- /* Read reference */
- if((*(src->shared->u.atomic.u.r.read))(src->shared->u.atomic.u.r.f, dxpl_id, s, conv_buf, buf_size) < 0)
- HGOTO_ERROR(H5E_DATATYPE, H5E_READERROR, FAIL, "can't read reference data")
+ for(elmtno = 0; elmtno < safe; elmtno++) {
+ size_t buf_size;
+
+ /* Get size of references */
+ if(0 == (buf_size = (*(src->shared->u.atomic.u.r.getsize))(s)))
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "incorrect size")
+
+ /* Check if conversion buffer is large enough, resize if necessary. */
+ if(conv_buf_size < buf_size) {
+ conv_buf_size = buf_size;
+ if(NULL == (conv_buf = H5FL_BLK_REALLOC(ref_seq, conv_buf, conv_buf_size)))
+ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed for type conversion")
+ HDmemset(conv_buf, 0, conv_buf_size);
+ } /* end if */
- /* Write reference to destination location */
- if((*(dst->shared->u.atomic.u.r.write))(dst->shared->u.atomic.u.r.f, dxpl_id, d, conv_buf, b, buf_size) < 0)
- HGOTO_ERROR(H5E_DATATYPE, H5E_WRITEERROR, FAIL, "can't write reference data")
+ /* Read reference */
+ if((*(src->shared->u.atomic.u.r.read))(src->shared->u.atomic.u.r.f, dxpl_id, s, conv_buf, buf_size) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_READERROR, FAIL, "can't read reference data")
- /* Advance pointers */
- s += s_stride;
- d += d_stride;
- b += b_stride;
- } /* end for */
+ /* Write reference to destination location */
+ if((*(dst->shared->u.atomic.u.r.write))(dst->shared->u.atomic.u.r.f, dxpl_id, d, conv_buf, b, buf_size, ref_type) < 0)
+ HGOTO_ERROR(H5E_DATATYPE, H5E_WRITEERROR, FAIL, "can't write reference data")
+
+ /* Advance pointers */
+ s += s_stride;
+ d += d_stride;
+ b += b_stride;
+ } /* end for */
+
+ /* Decrement number of elements left to convert */
+ nelmts -= safe;
+ } /* end while */
} /* end case */
break;
diff --git a/src/H5Tnative.c b/src/H5Tnative.c
index 7f536cf..abf36eb 100644
--- a/src/H5Tnative.c
+++ b/src/H5Tnative.c
@@ -124,7 +124,6 @@ done:
H5T_t *
H5T_get_native_type(H5T_t *dtype, H5T_direction_t direction, size_t *struct_align, size_t *offset, size_t *comp_size)
{
- H5T_t *dt; /* Datatype to make native */
H5T_t *super_type; /* Super type of VL, array and enum datatypes */
H5T_t *nat_super_type; /* Native form of VL, array & enum super datatype */
H5T_t *new_type = NULL; /* New native datatype */
@@ -216,53 +215,11 @@ H5T_get_native_type(H5T_t *dtype, H5T_direction_t direction, size_t *struct_alig
case H5T_REFERENCE:
{
- size_t align;
- size_t ref_size;
- int not_equal;
-
if(NULL == (ret_value = H5T_copy(dtype, H5T_COPY_TRANSIENT)))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "cannot retrieve float type")
-
- /* Decide if the datatype is an object reference. */
- if(NULL == (dt = (H5T_t *)H5I_object(H5T_STD_REF_OBJ_g)))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a datatype")
- not_equal = H5T_cmp(ret_value, dt, FALSE);
+ HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "cannot copy reference type")
/* Update size, offset and compound alignment for parent. */
- if(!not_equal) {
- align = H5T_HOBJREF_COMP_ALIGN_g;
- ref_size = sizeof(hobj_ref_t);
- } /* end if */
- else {
- /* Decide if the datatype is a dataset region reference. */
- if(NULL == (dt = (H5T_t *)H5I_object(H5T_STD_REF_DSETREG_g)))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a datatype")
- not_equal = H5T_cmp(ret_value, dt, FALSE);
-
- /* Update size, offset and compound alignment for parent. */
- if(!not_equal) {
- align = H5T_HDSETREGREF_COMP_ALIGN_g;
- ref_size = sizeof(hdset_reg_ref_t);
- } /* end if */
- else {
- /* Decide if the datatype is a dataset region reference. */
- if(NULL == (dt = (H5T_t *)H5I_object(H5T_STD_REF_REG_g)))
- HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "not a datatype")
- not_equal = H5T_cmp(ret_value, dt, FALSE);
-
- /* Update size, offset and compound alignment for parent. */
- if(!not_equal) {
- align = H5T_HREGREF_COMP_ALIGN_g;
- ref_size = sizeof(hreg_ref_t);
- } /* end if */
- else {
- align = H5T_HATTRREF_COMP_ALIGN_g;
- ref_size = sizeof(hattr_ref_t);
- } /* end else */
- } /* end else */
- } /* end else */
-
- if(H5T_cmp_offset(comp_size, offset, ref_size, (size_t)1, align, struct_align) < 0)
+ if(H5T_cmp_offset(comp_size, offset, sizeof(href_t), (size_t)1, H5T_HREF_COMP_ALIGN_g, struct_align) < 0)
HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, NULL, "cannot compute compound offset")
} /* end case */
break;
diff --git a/src/H5Tpkg.h b/src/H5Tpkg.h
index fdc3dd7..e7925b8 100644
--- a/src/H5Tpkg.h
+++ b/src/H5Tpkg.h
@@ -169,7 +169,7 @@ typedef size_t (*H5T_ref_getsizefunc_t)(const void *_ref);
typedef herr_t (*H5T_ref_readfunc_t)(H5F_t *f, hid_t dxpl_id, void *_ref,
void *buf, size_t buf_size);
typedef herr_t (*H5T_ref_writefunc_t)(H5F_t *f, hid_t dxpl_id, void *_ref,
- void *buf, void *_bg, size_t buf_size);
+ void *buf, void *_bg, size_t buf_size, H5R_type_t ref_type);
typedef struct H5T_atomic_t {
H5T_order_t order; /*byte order */
@@ -365,10 +365,7 @@ H5_DLLVAR size_t H5T_NATIVE_LDOUBLE_COMP_ALIGN_g;
H5_DLLVAR size_t H5T_POINTER_COMP_ALIGN_g;
H5_DLLVAR size_t H5T_HVL_COMP_ALIGN_g;
-H5_DLLVAR size_t H5T_HOBJREF_COMP_ALIGN_g;
-H5_DLLVAR size_t H5T_HDSETREGREF_COMP_ALIGN_g;
-H5_DLLVAR size_t H5T_HREGREF_COMP_ALIGN_g;
-H5_DLLVAR size_t H5T_HATTRREF_COMP_ALIGN_g;
+H5_DLLVAR size_t H5T_HREF_COMP_ALIGN_g;
/*
* Alignment information for native types. A value of N indicates that the
diff --git a/src/H5Tpublic.h b/src/H5Tpublic.h
index f27025c..bcbb518 100644
--- a/src/H5Tpublic.h
+++ b/src/H5Tpublic.h
@@ -265,9 +265,11 @@ H5_DLLVAR hid_t H5T_IEEE_F64LE_g;
#define H5T_STD_B64BE (H5OPEN H5T_STD_B64BE_g)
#define H5T_STD_B64LE (H5OPEN H5T_STD_B64LE_g)
#define H5T_STD_REF_OBJ (H5OPEN H5T_STD_REF_OBJ_g)
-#define H5T_STD_REF_DSETREG (H5OPEN H5T_STD_REF_DSETREG_g)
#define H5T_STD_REF_REG (H5OPEN H5T_STD_REF_REG_g)
#define H5T_STD_REF_ATTR (H5OPEN H5T_STD_REF_ATTR_g)
+#define H5T_STD_REF_EXT_OBJ (H5OPEN H5T_STD_REF_EXT_OBJ_g)
+#define H5T_STD_REF_EXT_REG (H5OPEN H5T_STD_REF_EXT_REG_g)
+#define H5T_STD_REF_EXT_ATTR (H5OPEN H5T_STD_REF_EXT_ATTR_g)
H5_DLLVAR hid_t H5T_STD_I8BE_g;
H5_DLLVAR hid_t H5T_STD_I8LE_g;
H5_DLLVAR hid_t H5T_STD_I16BE_g;
@@ -293,9 +295,11 @@ H5_DLLVAR hid_t H5T_STD_B32LE_g;
H5_DLLVAR hid_t H5T_STD_B64BE_g;
H5_DLLVAR hid_t H5T_STD_B64LE_g;
H5_DLLVAR hid_t H5T_STD_REF_OBJ_g;
-H5_DLLVAR hid_t H5T_STD_REF_DSETREG_g;
H5_DLLVAR hid_t H5T_STD_REF_REG_g;
H5_DLLVAR hid_t H5T_STD_REF_ATTR_g;
+H5_DLLVAR hid_t H5T_STD_REF_EXT_OBJ_g;
+H5_DLLVAR hid_t H5T_STD_REF_EXT_REG_g;
+H5_DLLVAR hid_t H5T_STD_REF_EXT_ATTR_g;
/*
* Types which are particular to Unix.
diff --git a/src/H5Tref.c b/src/H5Tref.c
index a55c2e4..a495e225 100644
--- a/src/H5Tref.c
+++ b/src/H5Tref.c
@@ -28,6 +28,7 @@
#include "H5Iprivate.h" /* IDs */
#include "H5MMprivate.h" /* Memory management */
#include "H5Pprivate.h" /* Property lists */
+#include "H5Rprivate.h" /* References */
#include "H5Tpkg.h" /* Datatypes */
/* Local functions */
@@ -35,11 +36,19 @@ static herr_t H5T__ref_reclaim_recurse(void *elem, const H5T_t *dt);
static size_t H5T__ref_mem_getsize(const void *_ref);
static herr_t H5T__ref_mem_read(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, size_t buf_size);
-static herr_t H5T__ref_mem_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size);
+static herr_t H5T__ref_mem_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size, H5R_type_t ref_type);
+
+static size_t H5T__obj_ref_mem_getsize(const void *_ref);
+static herr_t H5T__obj_ref_mem_read(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, size_t buf_size);
+static herr_t H5T__obj_ref_mem_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size, H5R_type_t ref_type);
static size_t H5T__ref_disk_getsize(const void *_ref);
static herr_t H5T__ref_disk_read(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, size_t buf_size);
-static herr_t H5T__ref_disk_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size);
+static herr_t H5T__ref_disk_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size, H5R_type_t ref_type);
+
+static size_t H5T__obj_ref_disk_getsize(const void *_ref);
+static herr_t H5T__obj_ref_disk_read(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, size_t buf_size);
+static herr_t H5T__obj_ref_disk_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *_buf, void *_bg, size_t buf_size, H5R_type_t ref_type);
/* Local variables */
@@ -77,18 +86,20 @@ H5T__ref_set_loc(const H5T_t *dt, H5F_t *f, H5T_loc_t loc)
/* Mark this type as being stored in memory */
dt->shared->u.atomic.u.r.loc = H5T_LOC_MEMORY;
- if((dt->shared->u.atomic.u.r.rtype == H5R_REGION) ||
- (dt->shared->u.atomic.u.r.rtype == H5R_ATTR)) {
- /* size in memory, disk size is different */
- dt->shared->size = sizeof(struct href_var);
+ /* size in memory, disk size is different */
+ dt->shared->size = sizeof(href_t);
- /* Set up the function pointers to access the region
+ if (dt->shared->u.atomic.u.r.rtype == H5R_OBJECT) {
+ /* Set up the function pointers to access the object
* reference in memory */
+ dt->shared->u.atomic.u.r.getsize = H5T__obj_ref_mem_getsize;
+ dt->shared->u.atomic.u.r.read = H5T__obj_ref_mem_read;
+ dt->shared->u.atomic.u.r.write = H5T__obj_ref_mem_write;
+ } else {
+ /* Set up the function pointers to access the reference in memory */
dt->shared->u.atomic.u.r.getsize = H5T__ref_mem_getsize;
dt->shared->u.atomic.u.r.read = H5T__ref_mem_read;
dt->shared->u.atomic.u.r.write = H5T__ref_mem_write;
- } else {
- HDassert(0 && "Invalid reference type");
}
/* Reset file ID (since this reference is in memory) */
@@ -101,21 +112,34 @@ H5T__ref_set_loc(const H5T_t *dt, H5F_t *f, H5T_loc_t loc)
/* Mark this type as being stored on disk */
dt->shared->u.atomic.u.r.loc = H5T_LOC_DISK;
- /*
- * Size of element on disk is 4 bytes for the length, plus the size
- * of an address in this file, plus 4 bytes for the size of a heap
- * ID. Memory size is different
- */
- dt->shared->size = (size_t) (2 * H5_SIZEOF_UINT32_T) + H5F_SIZEOF_ADDR(f);
-
- /*
- * Set up the function pointers to access the information on
- * disk. Region and attribute references are stored identically
- * on disk, so use the same functions
- */
- dt->shared->u.atomic.u.r.getsize = H5T__ref_disk_getsize;
- dt->shared->u.atomic.u.r.read = H5T__ref_disk_read;
- dt->shared->u.atomic.u.r.write = H5T__ref_disk_write;
+ if (dt->shared->u.atomic.u.r.rtype == H5R_OBJECT) {
+ /* Size of element on disk */
+ dt->shared->size = sizeof(haddr_t);
+
+ /*
+ * Set up the function pointers to access the information on
+ * disk
+ */
+ dt->shared->u.atomic.u.r.getsize = H5T__obj_ref_disk_getsize;
+ dt->shared->u.atomic.u.r.read = H5T__obj_ref_disk_read;
+ dt->shared->u.atomic.u.r.write = H5T__obj_ref_disk_write;
+ } else {
+ /*
+ * Size of element on disk is 4 bytes for the length, plus the size
+ * of an address in this file, plus 4 bytes for the size of a heap
+ * ID. Memory size is different
+ */
+ dt->shared->size = (size_t) (2 * H5_SIZEOF_UINT32_T) + H5F_SIZEOF_ADDR(f);
+
+ /*
+ * Set up the function pointers to access the information on
+ * disk. Region and attribute references are stored identically
+ * on disk, so use the same functions
+ */
+ dt->shared->u.atomic.u.r.getsize = H5T__ref_disk_getsize;
+ dt->shared->u.atomic.u.r.read = H5T__ref_disk_read;
+ dt->shared->u.atomic.u.r.write = H5T__ref_disk_write;
+ }
/* Set file ID (since this reference is on disk) */
dt->shared->u.atomic.u.r.f = f;
@@ -148,9 +172,9 @@ static size_t
H5T__ref_mem_getsize(const void *_ref)
{
#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
- const struct href_var *ref = (const struct href_var *)_ref;
+ const struct href_t *ref = (const struct href_t *)_ref;
#else
- struct href_var ref;
+ struct href_t ref;
#endif
FUNC_ENTER_NOAPI_NOINIT_NOERR
@@ -159,10 +183,10 @@ H5T__ref_mem_getsize(const void *_ref)
#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
HDassert(ref);
- FUNC_LEAVE_NOAPI(ref->buf_size)
+ FUNC_LEAVE_NOAPI(ref->obj_enc.buf_size)
#else
HDassert(_ref);
- HDmemcpy(&ref, _ref, sizeof(struct href_var));
+ HDmemcpy(&ref, _ref, sizeof(struct href_t));
FUNC_LEAVE_NOAPI(ref.buf_size)
#endif
@@ -182,9 +206,9 @@ H5T__ref_mem_read(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
void *_ref, void *buf, size_t buf_size)
{
#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
- const struct href_var *ref = (const struct href_var *)_ref;
+ const struct href_t *ref = (const struct href_t *)_ref;
#else
- struct href_var ref;
+ struct href_t ref;
#endif
FUNC_ENTER_NOAPI_NOINIT_NOERR
@@ -192,15 +216,15 @@ H5T__ref_mem_read(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
/* check parameters, copy data */
HDassert(buf);
#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
- HDassert(ref && ref->buf);
+ HDassert(ref && ref->obj_enc.buf);
- HDmemcpy(buf, ref->buf, buf_size);
+ HDmemcpy(buf, ref->obj_enc.buf, buf_size);
#else
HDassert(_ref);
- HDmemcpy(&ref, _ref, sizeof(struct href_var));
- HDassert(ref.buf);
+ HDmemcpy(&ref, _ref, sizeof(struct href_t));
+ HDassert(ref.obj_enc.buf);
- HDmemcpy(buf, ref.buf, buf_size);
+ HDmemcpy(buf, ref.obj_enc.buf, buf_size);
#endif
FUNC_LEAVE_NOAPI(SUCCEED)
@@ -217,9 +241,9 @@ H5T__ref_mem_read(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
*/
static herr_t
H5T__ref_mem_write(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
- void *_ref, void *buf, void H5_ATTR_UNUSED *_bg, size_t buf_size)
+ void *_ref, void *buf, void H5_ATTR_UNUSED *_bg, size_t buf_size, H5R_type_t ref_type)
{
- struct href_var ref;
+ struct href_t ref;
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI_NOINIT
@@ -229,26 +253,118 @@ H5T__ref_mem_write(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
HDassert(buf);
if (buf_size != 0) {
- if (NULL == (ref.buf = H5MM_malloc(buf_size)))
+ if (NULL == (ref.obj_enc.buf = H5MM_malloc(buf_size)))
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed for reference data")
/* Copy the data into the newly allocated buffer */
- HDmemcpy(ref.buf, buf, buf_size);
+ HDmemcpy(ref.obj_enc.buf, buf, buf_size);
} /* end if */
else
- ref.buf = NULL;
+ ref.obj_enc.buf = NULL;
/* Set the size */
- ref.buf_size = buf_size;
+ ref.obj_enc.buf_size = buf_size;
+
+ /* Set the type */
+ ref.ref_type = ref_type;
/* Set pointer in user's buffer with memcpy, to avoid alignment issues */
- HDmemcpy(_ref, &ref, sizeof(struct href_var));
+ HDmemcpy(_ref, &ref, sizeof(struct href_t));
done:
FUNC_LEAVE_NOAPI(ret_value)
} /* end H5T__ref_mem_write() */
/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_mem_getsize
+ *
+ * Purpose: Retrieves the size of a memory based object reference.
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static size_t
+H5T__obj_ref_mem_getsize(const void H5_ATTR_UNUSED *_ref)
+{
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ FUNC_LEAVE_NOAPI(sizeof(haddr_t))
+} /* end H5T__obj_ref_mem_getsize() */
+
+/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_mem_read
+ *
+ * Purpose: "Reads" the memory based object reference into a buffer
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+H5T__obj_ref_mem_read(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
+ void *_ref, void *buf, size_t buf_size)
+{
+#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
+ const struct href_t *ref = (const struct href_t *)_ref;
+#else
+ struct href_t ref;
+#endif
+
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ /* check parameters, copy data */
+ HDassert(buf);
+#ifdef H5_NO_ALIGNMENT_RESTRICTIONS
+ HDassert(ref);
+
+ HDmemcpy(buf, &ref->obj_addr, sizeof(haddr_t));
+#else
+ HDassert(_ref);
+ HDmemcpy(&ref, _ref, sizeof(struct href_t));
+
+ HDmemcpy(buf, &ref.obj_addr, sizeof(haddr_t));
+#endif
+
+ FUNC_LEAVE_NOAPI(SUCCEED)
+} /* end H5T__obj_ref_mem_read() */
+
+/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_mem_write
+ *
+ * Purpose: "Writes" the memory object reference from a buffer
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+H5T__obj_ref_mem_write(H5F_t H5_ATTR_UNUSED *f, hid_t H5_ATTR_UNUSED dxpl_id,
+ void *_ref, void *buf, void H5_ATTR_UNUSED *_bg, size_t buf_size, H5R_type_t ref_type)
+{
+ struct href_t ref;
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ /* check parameters */
+ HDassert(_ref);
+ HDassert(buf);
+ HDassert(buf_size == sizeof(haddr_t));
+
+ /* Copy the data into the newly allocated buffer */
+ HDmemcpy(&ref.obj_addr, buf, buf_size);
+
+ /* Set the type */
+ ref.ref_type = ref_type;
+
+ /* Set pointer in user's buffer with memcpy, to avoid alignment issues */
+ HDmemcpy(_ref, &ref, sizeof(struct href_t));
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5T__obj_ref_mem_write() */
+
+/*-------------------------------------------------------------------------
* Function: H5T__ref_disk_getsize
*
* Purpose: Retrieves the length of a disk based reference.
@@ -326,7 +442,7 @@ done:
*/
static herr_t
H5T__ref_disk_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *buf, void *_bg,
- size_t buf_size)
+ size_t buf_size, H5R_type_t H5_ATTR_UNUSED ref_type)
{
uint8_t *ref = (uint8_t *)_ref; /* Pointer to the user's information */
const uint8_t *bg = (const uint8_t *)_bg; /* Pointer to the old data */
@@ -340,9 +456,8 @@ H5T__ref_disk_write(H5F_t *f, hid_t dxpl_id, void *_ref, void *buf, void *_bg,
HDassert(buf_size == 0 || buf);
HDassert(f);
- /* TODO not sure if we need that but oh well... */
/* Free heap object for old data. */
- if(bg != NULL) {
+ if(bg != NULL) { /* TODO Should get rid of bg stuff */
H5HG_t bg_hobjid; /* "Background" reference's ID info */
/* Skip the length of the reference and heap object ID from background data. */
@@ -376,6 +491,75 @@ done:
} /* end H5T__ref_disk_write() */
/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_disk_getsize
+ *
+ * Purpose: Retrieves the length of a disk based object reference.
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static size_t
+H5T__obj_ref_disk_getsize(const void H5_ATTR_UNUSED *_ref)
+{
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ FUNC_LEAVE_NOAPI(sizeof(haddr_t))
+} /* end H5T__obj_ref_disk_getsize() */
+
+/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_disk_read
+ *
+ * Purpose: Reads the disk based object reference into a buffer
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+H5T__obj_ref_disk_read(H5F_t H5_ATTR_UNUSED *f, hid_t dxpl_id, void *_ref, void *buf,
+ size_t H5_ATTR_UNUSED buf_size)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ /* check parameters */
+ HDassert(_ref);
+ HDassert(buf);
+
+ HDmemcpy(buf, _ref, sizeof(haddr_t));
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5T__obj_ref_disk_read() */
+
+/*-------------------------------------------------------------------------
+ * Function: H5T__obj_ref_disk_write
+ *
+ * Purpose: Writes the disk based object reference from a buffer
+ *
+ * Return: Non-negative on success/Negative on failure
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+H5T__obj_ref_disk_write(H5F_t H5_ATTR_UNUSED *f, hid_t dxpl_id, void *_ref, void *buf, void *_bg,
+ size_t buf_size, H5R_type_t H5_ATTR_UNUSED ref_type)
+{
+ herr_t ret_value = SUCCEED; /* Return value */
+
+ FUNC_ENTER_NOAPI_NOINIT_NOERR
+
+ /* check parameters */
+ HDassert(_ref);
+ HDassert(buf_size == 0 || buf);
+
+ HDmemcpy(_ref, buf, sizeof(haddr_t));
+
+ FUNC_LEAVE_NOAPI(ret_value)
+} /* end H5T__obj_ref_disk_write() */
+
+/*-------------------------------------------------------------------------
* Function: H5T__ref_reclaim_recurse
*
* Purpose: Internal recursive routine to free reference datatypes
@@ -397,16 +581,13 @@ H5T__ref_reclaim_recurse(void *elem, const H5T_t *dt)
/* Check the datatype of this element */
switch(dt->shared->type) {
case H5T_REFERENCE:
- if((dt->shared->u.atomic.u.r.rtype == H5R_REGION) ||
- (dt->shared->u.atomic.u.r.rtype == H5R_ATTR)) {
- struct href_var *ref = (struct href_var *)elem;
-
- if(ref->buf_size != 0) {
- ref->buf = H5MM_xfree(ref->buf);
- } /* end if */
- } else {
- HDassert(0 && "Invalid reference type");
- } /* end else */
+ {
+ struct href_t *ref = (struct href_t *)elem;
+
+ if((ref->ref_type != H5R_OBJECT) && (ref->obj_enc.buf_size != 0)) {
+ ref->obj_enc.buf = H5MM_xfree(ref->obj_enc.buf);
+ } /* end if */
+ }
break;
/* Don't do anything for other types */
diff --git a/src/H5detect.c b/src/H5detect.c
index ad0205b..bfb952b 100644
--- a/src/H5detect.c
+++ b/src/H5detect.c
@@ -56,7 +56,7 @@ static const char *FileHeader = "\n\
#undef NDEBUG
#include "H5private.h"
#include "H5Tpublic.h"
-#include "H5Rpublic.h"
+#include "H5Rprivate.h"
#define MAXDETECT 64
@@ -1653,14 +1653,10 @@ detect_C99_floats(void)
static void
detect_alignments(void)
{
- /* Detect structure alignment for pointers, hvl_t, hobj_ref_t,
- * hdset_reg_ref_t, hattr_ref_t, hreg_ref_t */
+ /* Detect structure alignment for pointers, hvl_t, href_t */
DETECT_M(void *, POINTER, m_g[na_g]); na_g++;
DETECT_M(hvl_t, HVL, m_g[na_g]); na_g++;
- DETECT_M(hobj_ref_t, HOBJREF, m_g[na_g]); na_g++;
- DETECT_M(hdset_reg_ref_t, HDSETREGREF, m_g[na_g]); na_g++;
- DETECT_M(hreg_ref_t, HREGREF, m_g[na_g]); na_g++;
- DETECT_M(hattr_ref_t, HATTRREF, m_g[na_g]); na_g++;
+ DETECT_M(href_t, HREF, m_g[na_g]); na_g++;
}
diff --git a/src/H5trace.c b/src/H5trace.c
index ec4dcbf..9fd1007 100644
--- a/src/H5trace.c
+++ b/src/H5trace.c
@@ -36,6 +36,7 @@
#include "H5Dprivate.h" /* Datasets */
#include "H5Eprivate.h" /* Error handling */
#include "H5FDprivate.h" /* File drivers */
+#include "H5Rprivate.h" /* References */
#include "H5Ipkg.h" /* IDs */
#include "H5MMprivate.h" /* Memory management */
#include "H5Qprivate.h" /* Queries */
@@ -1762,9 +1763,8 @@ H5_trace(const double *returning, const char *func, const char *type, ...)
fprintf(out, "NULL");
} /* end if */
else {
- hobj_ref_t ref = va_arg(ap, hobj_ref_t); /*lint !e732 Loss of sign not really occuring */
-
- HDfprintf(out, "Reference Object=%a", ref);
+ fprintf(out, "OPAQUE TYPE");
+ goto error;
} /* end else */
break;
@@ -1884,8 +1884,8 @@ H5_trace(const double *returning, const char *func, const char *type, ...)
fprintf(out, "H5R_OBJECT");
break;
- case H5R_DATASET_REGION:
- fprintf(out, "H5R_DATASET_REGION");
+ case H5R_REGION:
+ fprintf(out, "H5R_REGION");
break;
case H5R_ATTR: