diff options
-rw-r--r-- | src/H5.c | 37 | ||||
-rw-r--r-- | src/H5D.c | 251 | ||||
-rw-r--r-- | src/H5Dfill.c | 52 | ||||
-rw-r--r-- | src/H5Dpublic.h | 1562 | ||||
-rw-r--r-- | src/H5Dscatgath.c | 195 | ||||
-rw-r--r-- | src/H5S.c | 69 | ||||
-rw-r--r-- | src/H5Shyper.c | 2 | ||||
-rw-r--r-- | src/H5Smpio.c | 28 | ||||
-rw-r--r-- | src/H5Snone.c | 2 | ||||
-rw-r--r-- | src/H5Spkg.h | 8 | ||||
-rw-r--r-- | src/H5Spoint.c | 46 | ||||
-rw-r--r-- | src/H5Sprivate.h | 3 | ||||
-rw-r--r-- | src/H5Spublic.h | 1298 | ||||
-rw-r--r-- | src/H5Sselect.c | 117 | ||||
-rw-r--r-- | test/tselect.c | 197 |
15 files changed, 3445 insertions, 422 deletions
@@ -254,6 +254,8 @@ H5_init_library(void) * It might not be initialized during normal file open. * When the application does not close the file, routines in the module might * be called via H5_term_library() when shutting down the file. + * The dataspace interface needs to be initialized so that future IDs for + * dataspaces work. */ if (H5E_init() < 0) HGOTO_ERROR(H5E_FUNC, H5E_CANTINIT, FAIL, "unable to initialize error interface") @@ -271,6 +273,8 @@ H5_init_library(void) HGOTO_ERROR(H5E_FUNC, H5E_CANTINIT, FAIL, "unable to initialize link interface") if (H5FS_init() < 0) HGOTO_ERROR(H5E_FUNC, H5E_CANTINIT, FAIL, "unable to initialize FS interface") + if (H5S_init() < 0) + HGOTO_ERROR(H5E_FUNC, H5E_CANTINIT, FAIL, "unable to initialize dataspace interface") /* Finish initializing interfaces that depend on the interfaces above */ if (H5VL_init_phase2() < 0) @@ -361,21 +365,26 @@ H5_term_library(void) /* Try to organize these so the "higher" level components get shut * down before "lower" level components that they might rely on. -QAK */ - pending += DOWN(L); - /* Close the "top" of various interfaces (IDs, etc) but don't shut - * down the whole interface yet, so that the object header messages - * get serialized correctly for entries in the metadata cache and the - * symbol table entry in the superblock gets serialized correctly, etc. - * all of which is performed in the 'F' shutdown. - */ - pending += DOWN(A_top); - pending += DOWN(D_top); - pending += DOWN(G_top); - pending += DOWN(M_top); - pending += DOWN(R_top); - pending += DOWN(S_top); - pending += DOWN(T_top); + /* Close down the user-facing interfaces, after the event sets */ + if (pending == 0) { + /* Close the interfaces dependent on others */ + pending += DOWN(L); + + /* Close the "top" of various interfaces (IDs, etc) but don't shut + * down the whole interface yet, so that the object header messages + * get serialized correctly for entries in the metadata cache and the + * symbol table entry in the superblock gets serialized correctly, etc. + * all of which is performed in the 'F' shutdown. + */ + pending += DOWN(A_top); + pending += DOWN(D_top); + pending += DOWN(G_top); + pending += DOWN(M_top); + pending += DOWN(R_top); + pending += DOWN(S_top); + pending += DOWN(T_top); + } /* end if */ /* Don't shut down the file code until objects in files are shut down */ if (pending == 0) @@ -53,6 +53,9 @@ hbool_t H5_PKG_INIT_VAR = FALSE; /* Library Private Variables */ /*****************************/ +/* Declare extern free list to manage the H5S_sel_iter_t struct */ +H5FL_EXTERN(H5S_sel_iter_t); + /* Declare extern the free list to manage blocks of type conversion data */ H5FL_BLK_EXTERN(type_conv); @@ -593,6 +596,254 @@ done: FUNC_LEAVE_API(ret_value) } /* end H5Dget_offset() */ + +/*------------------------------------------------------------------------- + * Function: H5Dscatter + * + * Purpose: Scatters data provided by the callback op to the + * destination buffer dst_buf, where the dimensions of + * dst_buf and the selection to be scattered to are specified + * by the dataspace dst_space_id. The type of the data to be + * scattered is specified by type_id. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * 14 Jan 2013 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Dscatter(H5D_scatter_func_t op, void *op_data, hid_t type_id, hid_t dst_space_id, void *dst_buf /*out*/) +{ + H5T_t * type; /* Datatype */ + H5S_t * dst_space; /* Dataspace */ + H5S_sel_iter_t *iter = NULL; /* Selection iteration info*/ + hbool_t iter_init = FALSE; /* Selection iteration info has been initialized */ + const void * src_buf = NULL; /* Source (contiguous) data buffer */ + size_t src_buf_nbytes = 0; /* Size of src_buf */ + size_t type_size; /* Datatype element size */ + hssize_t nelmts; /* Number of remaining elements in selection */ + size_t nelmts_scatter = 0; /* Number of elements to scatter to dst_buf */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE5("e", "DS*xiix", op, op_data, type_id, dst_space_id, dst_buf); + + /* Check args */ + if (op == NULL) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid callback function pointer") + if (NULL == (type = (H5T_t *)H5I_object_verify(type_id, H5I_DATATYPE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a datatype") + if (NULL == (dst_space = (H5S_t *)H5I_object_verify(dst_space_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") + if (dst_buf == NULL) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no destination buffer provided") + + /* Get datatype element size */ + if (0 == (type_size = H5T_GET_SIZE(type))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get datatype size") + + /* Get number of elements in dataspace */ + if ((nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(dst_space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") + + /* Allocate the selection iterator */ + if (NULL == (iter = H5FL_MALLOC(H5S_sel_iter_t))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTALLOC, FAIL, "can't allocate selection iterator") + + /* Initialize selection iterator */ + if (H5S_select_iter_init(iter, dst_space, type_size, 0) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to initialize selection iterator information") + iter_init = TRUE; + + /* Loop until all data has been scattered */ + while (nelmts > 0) { + /* Make callback to retrieve data */ + if (op(&src_buf, &src_buf_nbytes, op_data) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CALLBACK, FAIL, "callback operator returned failure") + + /* Calculate number of elements */ + nelmts_scatter = src_buf_nbytes / type_size; + + /* Check callback results */ + if (!src_buf) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback did not return a buffer") + if (src_buf_nbytes == 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback returned a buffer size of 0") + if (src_buf_nbytes % type_size) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "buffer size is not a multiple of datatype size") + if (nelmts_scatter > (size_t)nelmts) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback returned more elements than in selection") + + /* Scatter data */ + if (H5D__scatter_mem(src_buf, iter, nelmts_scatter, dst_buf) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "scatter failed") + + nelmts -= (hssize_t)nelmts_scatter; + } /* end while */ + +done: + /* Release selection iterator */ + if (iter_init && H5S_SELECT_ITER_RELEASE(iter) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "Can't release selection iterator") + if (iter) + iter = H5FL_FREE(H5S_sel_iter_t, iter); + + FUNC_LEAVE_API(ret_value) +} /* H5Dscatter() */ + +/*------------------------------------------------------------------------- + * Function: H5Dgather + * + * Purpose: Gathers data provided from the source buffer src_buf to + * contiguous buffer dst_buf, then calls the callback op. + * The dimensions of src_buf and the selection to be gathered + * are specified by the dataspace src_space_id. The type of + * the data to be gathered is specified by type_id. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Neil Fortner + * 16 Jan 2013 + * + *------------------------------------------------------------------------- + */ +herr_t +H5Dgather(hid_t src_space_id, const void *src_buf, hid_t type_id, size_t dst_buf_size, void *dst_buf /*out*/, + H5D_gather_func_t op, void *op_data) +{ + H5T_t * type; /* Datatype */ + H5S_t * src_space; /* Dataspace */ + H5S_sel_iter_t *iter = NULL; /* Selection iteration info*/ + hbool_t iter_init = FALSE; /* Selection iteration info has been initialized */ + size_t type_size; /* Datatype element size */ + hssize_t nelmts; /* Number of remaining elements in selection */ + size_t dst_buf_nelmts; /* Number of elements that can fit in dst_buf */ + size_t nelmts_gathered; /* Number of elements gathered from src_buf */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE7("e", "i*xizxDg*x", src_space_id, src_buf, type_id, dst_buf_size, dst_buf, op, op_data); + + /* Check args */ + if (NULL == (src_space = (H5S_t *)H5I_object_verify(src_space_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") + if (src_buf == NULL) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no source buffer provided") + if (NULL == (type = (H5T_t *)H5I_object_verify(type_id, H5I_DATATYPE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a datatype") + if (dst_buf_size == 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "destination buffer size is 0") + if (dst_buf == NULL) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no destination buffer provided") + + /* Get datatype element size */ + if (0 == (type_size = H5T_GET_SIZE(type))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get datatype size") + + /* Get number of elements in dst_buf_size */ + dst_buf_nelmts = dst_buf_size / type_size; + if (dst_buf_nelmts == 0) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, + "destination buffer is not large enough to hold one element") + + /* Get number of elements in dataspace */ + if ((nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(src_space)) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") + + /* If dst_buf is not large enough to hold all the elements, make sure there + * is a callback */ + if (((size_t)nelmts > dst_buf_nelmts) && (op == NULL)) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no callback supplied and destination buffer too small") + + /* Allocate the selection iterator */ + if (NULL == (iter = H5FL_MALLOC(H5S_sel_iter_t))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTALLOC, FAIL, "can't allocate selection iterator") + + /* Initialize selection iterator */ + if (H5S_select_iter_init(iter, src_space, type_size, 0) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to initialize selection iterator information") + iter_init = TRUE; + + /* Loop until all data has been scattered */ + while (nelmts > 0) { + /* Gather data */ + if (0 == + (nelmts_gathered = H5D__gather_mem(src_buf, iter, MIN(dst_buf_nelmts, (size_t)nelmts), dst_buf))) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "gather failed") + HDassert(nelmts_gathered == MIN(dst_buf_nelmts, (size_t)nelmts)); + + /* Make callback to process dst_buf */ + if (op && op(dst_buf, nelmts_gathered * type_size, op_data) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CALLBACK, FAIL, "callback operator returned failure") + + nelmts -= (hssize_t)nelmts_gathered; + HDassert(op || (nelmts == 0)); + } /* end while */ + +done: + /* Release selection iterator */ + if (iter_init && H5S_SELECT_ITER_RELEASE(iter) < 0) + HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "Can't release selection iterator") + if (iter) + iter = H5FL_FREE(H5S_sel_iter_t, iter); + + FUNC_LEAVE_API(ret_value) +} /* H5Dgather() */ + +/*-------------------------------------------------------------------------- + NAME + H5Dfill + PURPOSE + Fill a selection in memory with a value + USAGE + herr_t H5Dfill(fill, fill_type, space, buf, buf_type) + const void *fill; IN: Pointer to fill value to use + hid_t fill_type_id; IN: Datatype of the fill value + void *buf; IN/OUT: Memory buffer to fill selection within + hid_t buf_type_id; IN: Datatype of the elements in buffer + hid_t space_id; IN: Dataspace describing memory buffer & + containing selection to use. + RETURNS + Non-negative on success/Negative on failure. + DESCRIPTION + Use the selection in the dataspace to fill elements in a memory buffer. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + If "fill" parameter is NULL, use all zeros as fill value + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5Dfill(const void *fill, hid_t fill_type_id, void *buf, hid_t buf_type_id, hid_t space_id) +{ + H5S_t *space; /* Dataspace */ + H5T_t *fill_type; /* Fill-value datatype */ + H5T_t *buf_type; /* Buffer datatype */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_API(FAIL) + H5TRACE5("e", "*xi*xii", fill, fill_type_id, buf, buf_type_id, space_id); + + /* Check args */ + if (buf == NULL) + HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid buffer") + if (NULL == (space = (H5S_t *)H5I_object_verify(space_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a dataspace") + if (NULL == (fill_type = (H5T_t *)H5I_object_verify(fill_type_id, H5I_DATATYPE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a datatype") + if (NULL == (buf_type = (H5T_t *)H5I_object_verify(buf_type_id, H5I_DATATYPE))) + HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a datatype") + + /* Fill the selection in the memory buffer */ + if (H5D__fill(fill, fill_type, buf, buf_type, space) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTENCODE, FAIL, "filling selection failed") + +done: + FUNC_LEAVE_API(ret_value) +} /* H5Dfill() */ + /*------------------------------------------------------------------------- * Function: H5Diterate * diff --git a/src/H5Dfill.c b/src/H5Dfill.c index b7ecdc9..fe98487 100644 --- a/src/H5Dfill.c +++ b/src/H5Dfill.c @@ -85,58 +85,6 @@ H5FL_EXTERN(H5S_sel_iter_t); /*-------------------------------------------------------------------------- NAME - H5Dfill - PURPOSE - Fill a selection in memory with a value - USAGE - herr_t H5Dfill(fill, fill_type, space, buf, buf_type) - const void *fill; IN: Pointer to fill value to use - hid_t fill_type_id; IN: Datatype of the fill value - void *buf; IN/OUT: Memory buffer to fill selection within - hid_t buf_type_id; IN: Datatype of the elements in buffer - hid_t space_id; IN: Dataspace describing memory buffer & - containing selection to use. - RETURNS - Non-negative on success/Negative on failure. - DESCRIPTION - Use the selection in the dataspace to fill elements in a memory buffer. - GLOBAL VARIABLES - COMMENTS, BUGS, ASSUMPTIONS - If "fill" parameter is NULL, use all zeros as fill value - EXAMPLES - REVISION LOG ---------------------------------------------------------------------------*/ -herr_t -H5Dfill(const void *fill, hid_t fill_type_id, void *buf, hid_t buf_type_id, hid_t space_id) -{ - H5S_t *space; /* Dataspace */ - H5T_t *fill_type; /* Fill-value datatype */ - H5T_t *buf_type; /* Buffer datatype */ - herr_t ret_value = SUCCEED; /* Return value */ - - FUNC_ENTER_API(FAIL) - H5TRACE5("e", "*xi*xii", fill, fill_type_id, buf, buf_type_id, space_id); - - /* Check args */ - if (buf == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid buffer") - if (NULL == (space = (H5S_t *)H5I_object_verify(space_id, H5I_DATASPACE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a dataspace") - if (NULL == (fill_type = (H5T_t *)H5I_object_verify(fill_type_id, H5I_DATATYPE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a datatype") - if (NULL == (buf_type = (H5T_t *)H5I_object_verify(buf_type_id, H5I_DATATYPE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, 0, "not a datatype") - - /* Fill the selection in the memory buffer */ - if (H5D__fill(fill, fill_type, buf, buf_type, space) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTENCODE, FAIL, "filling selection failed") - -done: - FUNC_LEAVE_API(ret_value) -} /* H5Dfill() */ - -/*-------------------------------------------------------------------------- - NAME H5D__fill PURPOSE Fill a selection in memory with a value (internal version) diff --git a/src/H5Dpublic.h b/src/H5Dpublic.h index 3c1a2de..0e2474a 100644 --- a/src/H5Dpublic.h +++ b/src/H5Dpublic.h @@ -39,30 +39,41 @@ /* Public Typedefs */ /*******************/ -/* Values for the H5D_LAYOUT property */ +//! <!-- [H5D_layout_t_snip] --> +/** + * Values for the H5D_LAYOUT property + */ typedef enum H5D_layout_t { H5D_LAYOUT_ERROR = -1, - H5D_COMPACT = 0, /*raw data is very small */ - H5D_CONTIGUOUS = 1, /*the default */ - H5D_CHUNKED = 2, /*slow and fancy */ - H5D_VIRTUAL = 3, /*actual data is stored in other datasets */ - H5D_NLAYOUTS = 4 /*this one must be last! */ + H5D_COMPACT = 0, /**< raw data is very small */ + H5D_CONTIGUOUS = 1, /**< the default */ + H5D_CHUNKED = 2, /**< slow and fancy */ + H5D_VIRTUAL = 3, /**< actual data is stored in other datasets */ + H5D_NLAYOUTS = 4 /**< this one must be last! */ } H5D_layout_t; +//! <!-- [H5D_layout_t_snip] --> -/* Types of chunk index data structures */ +//! <!-- [H5D_chunk_index_t_snip] --> +/** + * Types of chunk index data structures + */ typedef enum H5D_chunk_index_t { - H5D_CHUNK_IDX_BTREE = 0, /* v1 B-tree index (default) */ + H5D_CHUNK_IDX_BTREE = 0, /**< v1 B-tree index (default) */ H5D_CHUNK_IDX_SINGLE = - 1, /* Single Chunk index (cur dims[]=max dims[]=chunk dims[]; filtered & non-filtered) */ - H5D_CHUNK_IDX_NONE = 2, /* Implicit: No Index (H5D_ALLOC_TIME_EARLY, non-filtered, fixed dims) */ - H5D_CHUNK_IDX_FARRAY = 3, /* Fixed array (for 0 unlimited dims) */ - H5D_CHUNK_IDX_EARRAY = 4, /* Extensible array (for 1 unlimited dim) */ - H5D_CHUNK_IDX_BT2 = 5, /* v2 B-tree index (for >1 unlimited dims) */ - H5D_CHUNK_IDX_NTYPES /* This one must be last! */ + 1, /**< Single Chunk index (cur dims[]=max dims[]=chunk dims[]; filtered & non-filtered) */ + H5D_CHUNK_IDX_NONE = 2, /**< Implicit: No Index (#H5D_ALLOC_TIME_EARLY, non-filtered, fixed dims) */ + H5D_CHUNK_IDX_FARRAY = 3, /**< Fixed array (for 0 unlimited dims) */ + H5D_CHUNK_IDX_EARRAY = 4, /**< Extensible array (for 1 unlimited dim) */ + H5D_CHUNK_IDX_BT2 = 5, /**< v2 B-tree index (for >1 unlimited dims) */ + H5D_CHUNK_IDX_NTYPES /**< This one must be last! */ } H5D_chunk_index_t; +//! <!-- [H5D_chunk_index_t_snip] --> -/* Values for the space allocation time property */ +//! <!-- [H5D_alloc_time_t_snip] --> +/** + * Values for the space allocation time property + */ typedef enum H5D_alloc_time_t { H5D_ALLOC_TIME_ERROR = -1, H5D_ALLOC_TIME_DEFAULT = 0, @@ -70,51 +81,84 @@ typedef enum H5D_alloc_time_t { H5D_ALLOC_TIME_LATE = 2, H5D_ALLOC_TIME_INCR = 3 } H5D_alloc_time_t; +//! <!-- [H5D_alloc_time_t_snip] --> -/* Values for the status of space allocation */ +//! <!-- [H5D_space_status_t_snip] --> +/** + * Values for the status of space allocation + */ typedef enum H5D_space_status_t { H5D_SPACE_STATUS_ERROR = -1, H5D_SPACE_STATUS_NOT_ALLOCATED = 0, H5D_SPACE_STATUS_PART_ALLOCATED = 1, H5D_SPACE_STATUS_ALLOCATED = 2 } H5D_space_status_t; +//! <!-- [H5D_space_status_t_snip] --> -/* Values for time of writing fill value property */ +//! <!-- [H5D_fill_time_t_snip] --> +/** + * Values for time of writing fill value property + */ typedef enum H5D_fill_time_t { H5D_FILL_TIME_ERROR = -1, H5D_FILL_TIME_ALLOC = 0, H5D_FILL_TIME_NEVER = 1, H5D_FILL_TIME_IFSET = 2 } H5D_fill_time_t; +//! <!-- [H5D_fill_time_t_snip] --> -/* Values for fill value status */ +//! <!-- [H5D_fill_value_t_snip] --> +/** + * Values for fill value status + */ typedef enum H5D_fill_value_t { H5D_FILL_VALUE_ERROR = -1, H5D_FILL_VALUE_UNDEFINED = 0, H5D_FILL_VALUE_DEFAULT = 1, H5D_FILL_VALUE_USER_DEFINED = 2 } H5D_fill_value_t; +//! <!-- [H5D_fill_value_t_snip] --> -/* Values for VDS bounds option */ +//! <!-- [H5D_vds_view_t_snip] --> +/** + * Values for VDS bounds option + */ typedef enum H5D_vds_view_t { H5D_VDS_ERROR = -1, H5D_VDS_FIRST_MISSING = 0, H5D_VDS_LAST_AVAILABLE = 1 } H5D_vds_view_t; +//! <!-- [H5D_vds_view_t_snip] --> -/* Callback for H5Pset_append_flush() in a dataset access property list */ +//! <!-- [H5D_append_cb_t_snip] --> +/** + * Callback for H5Pset_append_flush() in a dataset access property list + */ typedef herr_t (*H5D_append_cb_t)(hid_t dataset_id, hsize_t *cur_dims, void *op_data); +//! <!-- [H5D_append_cb_t_snip] --> -/* Define the operator function pointer for H5Diterate() */ +//! <!-- [H5D_operator_t_snip] --> +/** + * Define the operator function pointer for H5Diterate() + */ typedef herr_t (*H5D_operator_t)(void *elem, hid_t type_id, unsigned ndim, const hsize_t *point, void *operator_data); +//! <!-- [H5D_operator_t_snip] --> -/* Define the operator function pointer for H5Dscatter() */ +//! <!-- [H5D_scatter_func_t_snip] --> +/** + * Define the operator function pointer for H5Dscatter() + */ typedef herr_t (*H5D_scatter_func_t)(const void **src_buf /*out*/, size_t *src_buf_bytes_used /*out*/, void *op_data); +//! <!-- [H5D_scatter_func_t_snip] --> -/* Define the operator function pointer for H5Dgather() */ +//! <!-- [H5D_gather_func_t_snip] --> +/** + * Define the operator function pointer for H5Dgather() + */ typedef herr_t (*H5D_gather_func_t)(const void *dst_buf, size_t dst_buf_bytes_used, void *op_data); +//! <!-- [H5D_gather_func_t_snip] --> /********************/ /* Public Variables */ @@ -127,45 +171,1269 @@ typedef herr_t (*H5D_gather_func_t)(const void *dst_buf, size_t dst_buf_bytes_us extern "C" { #endif -H5_DLL hid_t H5Dcreate2(hid_t loc_id, const char *name, hid_t type_id, hid_t space_id, hid_t lcpl_id, - hid_t dcpl_id, hid_t dapl_id); -H5_DLL hid_t H5Dcreate_anon(hid_t file_id, hid_t type_id, hid_t space_id, hid_t plist_id, hid_t dapl_id); -H5_DLL hid_t H5Dopen2(hid_t file_id, const char *name, hid_t dapl_id); -H5_DLL herr_t H5Dclose(hid_t dset_id); -H5_DLL hid_t H5Dget_space(hid_t dset_id); -H5_DLL herr_t H5Dget_space_status(hid_t dset_id, H5D_space_status_t *allocation); -H5_DLL hid_t H5Dget_type(hid_t dset_id); -H5_DLL hid_t H5Dget_create_plist(hid_t dset_id); -H5_DLL hid_t H5Dget_access_plist(hid_t dset_id); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Creates a new dataset and links it into the file + * + * \fgdta_loc_id + * \param[in] name Name of the dataset to create + * \type_id + * \space_id + * \lcpl_id + * \dcpl_id + * \dapl_id + * + * \return \hid_t{dataset} + * + * \details H5Dcreate2() creates a new dataset named \p name at + * the location specified by \p loc_id, and associates constant + * and initial persistent properties with that dataset, including + * the datatype \p dtype_id, the dataspace \p space_id, and + * other properties as specified by the dataset creation property + * list \p dcpl_id and the access property list \p dapl_id, + * respectively. Once created, the dataset is opened for access. + * + * \p loc_id may specify a file, group, dataset, named datatype, + * or attribute. If an attribute, dataset, or named datatype is + * specified then the dataset will be created at the location + * where the attribute, dataset, or named datatype is attached. + * + * \p name may be either an absolute path in the file or a relative + * path from \p loc_id naming the dataset. + * + * \p dtype_id specifies the datatype of each data element as stored + * in the file. If \p dtype_id is either a fixed-length or + * variable-length string, it is important to set the string length + * when defining the datatype. String datatypes are derived from + * #H5T_C_S1 (or #H5T_FORTRAN_S1 for Fortran codes), which defaults + * to 1 character in size. + * + * If \p dtype_id is a committed datatype, and if the file location + * associated with the committed datatype is different from the + * file location where the dataset will be created, the datatype + * is copied and converted to a transient type. + * + * The link creation property list, \p lcpl_id, governs creation + * of the link(s) by which the new dataset is accessed and the + * creation of any * intermediate groups that may be missing. + * + * The datatype and dataspace properties and the dataset creation + * and access property lists are attached to the dataset, so the + * caller may derive new datatypes, dataspaces, and creation and + * access properties from the old ones and reuse them in calls to + * create additional datasets. Once created, the dataset can be + * read from or written to. Reading data from a datatset that was + * not previously written, the HDF5 library will return default + * or user-defined fill values. + * + * To conserve and release resources, the dataset should be closed + * when access is no longer required. + * + * \since 1.8.0 + * + * \see H5Dopen2(), H5Dclose(), H5Tset_size() + * + */ +H5_DLL hid_t H5Dcreate2(hid_t loc_id, const char *name, hid_t type_id, hid_t space_id, hid_t lcpl_id, + hid_t dcpl_id, hid_t dapl_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Creates a dataset in a file without linking it into the file + * structure + * + * \fgdta_loc_id + * \type_id + * \space_id + * \dcpl_id + * \dapl_id + * + * \return \hid_t{dataset} + * + * \details H5Dcreate_anon() creates a dataset in the file specified + * by \p loc_id. + * + * \p loc_id may specify a file, group, dataset, named datatype, + * or attribute. If an attribute, dataset, or named datatype is + * specified then the dataset will be created at the location + * where the attribute, dataset, or named datatype is attached. + * + * The dataset’s datatype and dataspace are specified by + * \p type_id and \p space_id, respectively. These are the + * datatype and dataspace of the dataset as it will exist in + * the file, which may differ from the datatype and dataspace + * in application memory. + * + * Dataset creation property list and dataset access creation + * property list are specified by \p dcpl_id and \p dapl_id. + * + * H5Dcreate_anon() returns a new dataset identifier. Using + * this identifier, the new dataset must be linked into the + * HDF5 file structure with H5Olink() or it will be deleted + * from the file when the file is closed. + * + * See H5Dcreate2() for further details and considerations on + * the use of H5Dcreate2() and H5Dcreate_anon(). + * + * The differences between this function and H5Dcreate2() are + * as follows: + * \li H5Dcreate_anon() explicitly includes a dataset access property + * list. H5Dcreate() always uses default dataset access properties. + * + * \li H5Dcreate_anon() neither provides the new dataset’s name nor + * links it into the HDF5 file structure; those actions must be + * performed separately through a call to H5Olink(), which offers + * greater control over linking. + * + * A dataset created with this function should be closed with + * H5Dclose() when the dataset is no longer needed so that resource + * leaks will not develop. + * + * \since 1.8.0 + * + * \see H5Olink(), H5Dcreate(), Using Identifiers + * + */ +H5_DLL hid_t H5Dcreate_anon(hid_t loc_id, hid_t type_id, hid_t space_id, hid_t dcpl_id, hid_t dapl_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Creates a new dataset and links it into the file + * + * \fgdta_loc_id + * \param[in] name Name of the dataset to open + * \dapl_id + * + * \return \hid_t{dataset} + * + * \details H5Dopen2() opens the existing dataset specified + * by a location identifier and name, \p loc_id and \p name, + * respectively. + * + * \p loc_id may specify a file, group, dataset, named datatype, + * or attribute. If an attribute, dataset, or named datatype is + * specified then the dataset will be opened at the location + * where the attribute, dataset, or named datatype is attached. + * + * The dataset access property list, \p dapl_id, provides + * information regarding access to the dataset. + * + * To conserve and release resources, the dataset should be closed + * when access is no longer required. + * + * \since 1.8.0 + * + * \see H5Dcreate2(), H5Dclose() + * + */ +H5_DLL hid_t H5Dopen2(hid_t loc_id, const char *name, hid_t dapl_id); + + +/** + * -------------------------------------------------------------------------- + *\ingroup H5D + * + * \brief Returns an identifier for a copy of the dataspace for a dataset + * + * \dset_id + * + * \return \hid_t{dataspace} + * + * \details H5Dget_space() makes a copy of the dataspace of + * the dataset specified by \p dset_id. The function returns an + * identifier for the new copy of the dataspace. + * + * A dataspace identifier returned from this function should + * be released with H5Sclose() when the identifier is no longer + * needed so that resource leaks will not occur. + * + * \see H5Sclose() + * + */ +H5_DLL hid_t H5Dget_space(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * \todo Document this function! + */ +H5_DLL herr_t H5Dget_space_status(hid_t dset_id, H5D_space_status_t *allocation); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns an identifier for a copy of the datatype for a dataset + * + * \dset_id + * + * \return \hid_t{datatype} + * + * \details H5Dget_type() returns an identifier of a copy of + * the datatype for a dataset. + * + * If a dataset has a named datatype, then an identifier to the + * opened datatype is returned. Otherwise, the returned datatype + * is read-only. If atomization of the datatype fails, then the + * datatype is closed. + * + * A datatype identifier returned from this function should be + * released with H5Tclose() when the identifier is no longer + * needed to prevent resource leaks. + * + * \note Datatype Identifiers + * + * Please note that the datatype identifier is actually an object + * identifier or a handle returned from opening the datatype. It + * is not persistent and its value can be different from one HDF5 + * session to the next. + * + * H5Tequal() can be used to compare datatypes. + * + * HDF5 High Level APIs that may also be of interest are: + * + * H5LTdtype_to_text() creates a text description of a + * datatype. H5LTtext_to_dtype() creates an HDF5 datatype + * given a text description. + * + */ +H5_DLL hid_t H5Dget_type(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns an identifier for a copy of the dataset creation + * property list for a dataset + * + * \dset_id + * + * \return \hid_t{dataset creation property list} + * + * \details H5Dget_create_plist() returns an identifier for + * a copy of the dataset creation property list associated with + * the dataset specified by \p dset_id. + * + * The creation property list identifier should be released + * with H5Pclose() to prevent resource leaks. + * + */ +H5_DLL hid_t H5Dget_create_plist(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns the dataset access property list associated with + * a dataset + * + * \dset_id + * + * \return \hid_t{dataset access property list} + * + * \details H5Dget_access_plist() returns a copy of the + * dataset access property list used to open the specified + * dataset, \p dset_id. Modifications to the returned property + * list will have no effect on the dataset it was retrieved from. + * + * The chunk cache parameters in the returned property lists will + * be those used by the dataset. If the properties in the file + * access property list were used to determine the dataset's + * chunk cache configuration, then those properties will be + * present in the returned dataset access property list. If + * the dataset does not use a chunked layout, then the chunk + * cache properties will be set to the default. The chunk cache + * properties in the returned list are considered to be “set”, + * and any use of this list will override the corresponding + * properties in the file’s file access property list. + * + * All link access properties in the returned list will be set + * to the default values. + * + * The access property list identifier should be released with + * H5Pclose() when the identifier is no longer needed so that + * resource leaks will not develop. + * + * \since 1.8.3 + * + */ +H5_DLL hid_t H5Dget_access_plist(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns the amount of storage allocated for a dataset + * + * \dset_id + * + * \return Returns the amount of storage space, in bytes, or 0 (zero). + * + * \details H5Dget_storage_size() returns the amount of storage, + * in bytes, that is allocated in the file for the raw data of + * the dataset specified by \p dset_id. + * + * \note The amount of storage in this case is the storage + * allocated in the written file, which will typically differ + * from the space required to hold a dataset in working memory. + * + * \li For contiguous datasets, the returned size equals the current + * allocated size of the raw data. + * \li For unfiltered chunked datasets, the returned size is the + * number of allocated chunks times the chunk size. + * \li For filtered chunked datasets, the returned size is the + * space required to store the filtered data. For example, if a + * compression filter is in use, H5Dget_storage_size() will return + * the total space required to store the compressed chunks. + * + * H5Dget_storage_size() reports only the space required to store + * the data, not including that of any metadata. + * + * \attention H5Dget_storage_size() does not differentiate between 0 (zero), + * the value returned for the storage size of a dataset + * with no stored values, and 0 (zero), the value returned to + * indicate an error. + * + * \note Note that H5Dget_storage_size() is not generally an + * appropriate function to use when determining the amount + * of memory required to work with a dataset. In such + * circumstances, you must determine the number of data + * points in a dataset and the size of an individual data + * element. H5Sget_simple_extent_npoints() and H5Tget_size() + * can be used to get that information. + * + */ H5_DLL hsize_t H5Dget_storage_size(hid_t dset_id); -H5_DLL herr_t H5Dget_chunk_storage_size(hid_t dset_id, const hsize_t *offset, hsize_t *chunk_bytes); -H5_DLL herr_t H5Dget_num_chunks(hid_t dset_id, hid_t fspace_id, hsize_t *nchunks); -H5_DLL herr_t H5Dget_chunk_info_by_coord(hid_t dset_id, const hsize_t *coord, unsigned *filter_mask, - haddr_t *addr, hsize_t *size); -H5_DLL herr_t H5Dget_chunk_info(hid_t dset_id, hid_t fspace_id, hsize_t chk_idx, hsize_t *coord, - unsigned *filter_mask, haddr_t *addr, hsize_t *size); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns the amount of storage allocated within the file for a + * raw data chunk in a dataset + * + * \dset_id + * \param[in] offset Logical offset in the dataset for the chunk to query + * \param[out] chunk_bytes The size in bytes for the chunk + * + * \return \herr_t + * + * \details H5Dget_chunk_storage_size() returns the size in bytes + * allocated in the file for a raw data chunk as specified by + * its logical \p offset in the dataset \p dset_id. The size is + * returned in \p chunk_nbytes. It is the size of the compressed + * data if the chunk is filtered and the size may be zero if no + * storage is allocated yet for the dataset. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dget_chunk_storage_size(hid_t dset_id, const hsize_t *offset, hsize_t *chunk_bytes); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Retrieves number of chunks that have nonempty intersection with a + * specified selection + * + * \dset_id + * \param[in] fspace_id File dataspace selection identifier + * \param[out] nchunks Number of chunks in the selection + * + * \return \herr_t + * + * \details H5Dget_num_chunks() retrieves the number of chunks + * nchunks in a set of selected elements specified by \p fspace_id + * for a dataset specified by the identifier \p dset_id. If \p + * fspace_id is #H5S_ALL, the function will retrieve the total + * number of chunks stored for the dataset. + * + * \p fspace_id specifies the file dataspace selection. It is + * intended to take #H5S_ALL for specifying the current selection. + * + * \note Please be aware that this function currently does not + * support non-trivial selections, thus \p fspace_id has no + * effect. Also, the implementation does not handle the #H5S_ALL + * macro correctly. As a workaround, application can get + * the dataspace for the dataset using H5Dget_space() and pass that + * in for \p fspace_id. This will be fixed in coming releases. + * + * \since 1.10.5 + * + */ +H5_DLL herr_t H5Dget_num_chunks(hid_t dset_id, hid_t fspace_id, hsize_t *nchunks); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Retrieves information about a chunk specified by its coordinates + * + * \dset_id + * \param[in] offset Logical position of the chunk’s first element + * \param[out] filter_mask Indicating filters used with the chunk when written + * \param[out] addr Chunk address in the file + * \param[out] size Chunk size in bytes, 0 if chunk doesn’t exist + * + * \return \herr_t + * + * \details H5Dget_chunk_info_by_coord() retrieves the \p filter_mask, \p size, + * and \p addr for a chunk in the dataset specified by \p dset_id, + * using the coordinates specified by \p offset. + * + * If the queried chunk does not exist in the file, \p size will + * be set to 0, \p addr to \c HADDR_UNDEF, and the buffer \p + * filter_mask will not be modified. + * + * \p offset is a pointer to a one-dimensional array with a size + * equal to the dataset’s rank. Each element is the logical + * position of the chunk’s first element in a dimension. + * + * \since 1.10.5 + * + */ +H5_DLL herr_t H5Dget_chunk_info_by_coord(hid_t dset_id, const hsize_t *offset, unsigned *filter_mask, + haddr_t *addr, hsize_t *size); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Retrieves information about a chunk specified by its index + * + * \dset_id + * \param[in] fspace_id File dataspace selection identifier (See Note below) + * \param[in] chk_idx Index of the chunk + * \param[out] offset Logical position of the chunk’s first element + * \param[out] filter_mask Indicating filters used with the chunk when written + * \param[out] addr Chunk address in the file + * \param[out] size Chunk size in bytes, 0 if chunk doesn’t exist + * + * \return \herr_t + * + * \details H5Dget_chunk_info() retrieves the offset coordinates + * offset, filter mask filter_mask, size size and address addr for + * the dataset specified by the identifier dset_id and the chunk + * specified by the index index. The chunk belongs to a set of + * chunks in the selection specified by fspace_id. If the queried + * chunk does not exist in the file, the size will be set to 0 and + * address to \c HADDR_UNDEF. The value pointed to by filter_mask will + * not be modified. NULL can be passed in for any \p out parameters. + * + * \p chk_idx is the chunk index in the selection. Index value + * may have a value of 0 up to the number of chunks stored in + * the file that have a nonempty intersection with the file + * dataspace selection + * + * \note As of 1.10.5, the dataspace intersection is not yet + * supported, hence, the index is of all the written chunks. + * + * \p fspace_id specifies the file dataspace selection. It is + * intended to take #H5S_ALL for specifying the current selection. + * + * \note Please be aware that this function currently does not + * support non-trivial selections, thus \p fspace_id has no + * effect. Also, the implementation does not handle the #H5S_ALL + * macro correctly. As a workaround, application can get + * the dataspace for the dataset using H5Dget_space() and pass that + * in for \p fspace_id. This will be fixed in coming releases. + * + * \since 1.10.5 + * + */ +H5_DLL herr_t H5Dget_chunk_info(hid_t dset_id, hid_t fspace_id, hsize_t chk_idx, hsize_t *offset, + unsigned *filter_mask, haddr_t *addr, hsize_t *size); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Returns dataset address in file + * + * \dset_id + * + * \return Returns the offset in bytes; otherwise, returns \c HADDR_UNDEF, + * a negative value. + * + * \details H5Dget_offset() returns the address in the file of + * the dataset, \p dset_id. That address is expressed as the + * offset in bytes from the beginning of the file. + * + * \since 1.6.0 + * + */ H5_DLL haddr_t H5Dget_offset(hid_t dset_id); -H5_DLL herr_t H5Dread(hid_t dset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, - hid_t plist_id, void *buf /*out*/); -H5_DLL herr_t H5Dwrite(hid_t dset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, - hid_t plist_id, const void *buf); -H5_DLL herr_t H5Dwrite_chunk(hid_t dset_id, hid_t dxpl_id, uint32_t filters, const hsize_t *offset, - size_t data_size, const void *buf); -H5_DLL herr_t H5Dread_chunk(hid_t dset_id, hid_t dxpl_id, const hsize_t *offset, uint32_t *filters, - void *buf); -H5_DLL herr_t H5Diterate(void *buf, hid_t type_id, hid_t space_id, H5D_operator_t op, void *operator_data); -H5_DLL herr_t H5Dvlen_get_buf_size(hid_t dataset_id, hid_t type_id, hid_t space_id, hsize_t *size); -H5_DLL herr_t H5Dfill(const void *fill, hid_t fill_type, void *buf, hid_t buf_type, hid_t space); -H5_DLL herr_t H5Dset_extent(hid_t dset_id, const hsize_t size[]); -H5_DLL herr_t H5Dflush(hid_t dset_id); -H5_DLL herr_t H5Drefresh(hid_t dset_id); -H5_DLL herr_t H5Dscatter(H5D_scatter_func_t op, void *op_data, hid_t type_id, hid_t dst_space_id, - void *dst_buf); -H5_DLL herr_t H5Dgather(hid_t src_space_id, const void *src_buf, hid_t type_id, size_t dst_buf_size, - void *dst_buf, H5D_gather_func_t op, void *op_data); -H5_DLL herr_t H5Ddebug(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Reads raw data from a dataset into a provided buffer + * + * \dset_id Identifier of the dataset to read from + * \param[in] mem_type_id Identifier of the memory datatype + * \param[in] mem_space_id Identifier of the memory dataspace + * \param[in] file_space_id Identifier of the dataset's dataspace in the file + * \param[in] dxpl_id Identifier of a transfer property list + * \param[out] buf Buffer to receive data read from file + * + * \return \herr_t + * + * \details H5Dread() reads a dataset, specified by its identifier + * \p dset_id, from the file into an application memory buffer \p + * buf. Data transfer properties are defined by the argument \p + * dxpl_id. The memory datatype of the (partial) dataset + * is identified by the identifier \p mem_type_id. The part + * of the dataset to read is defined by \p mem_space_id and \p + * file_space_id. + * + * \p file_space_id is used to specify only the selection within + * the file dataset's dataspace. Any dataspace specified in \p + * file_space_id is ignored by the library and the dataset's + * dataspace is always used. \p file_space_id can be the constant + * #H5S_ALL, which indicates that the entire file dataspace, + * as defined by the current dimensions of the dataset, is to + * be selected. + * + * \p mem_space_id is used to specify both the memory dataspace + * and the selection within that dataspace. \p mem_space_id can + * be the constant #H5S_ALL, in which case the file dataspace is + * used for the memory dataspace and the selection defined with \p + * file_space_id is used for the selection within that dataspace. + * + * If raw data storage space has not been allocated for the dataset + * and a fill value has been defined, the returned buffer \p buf + * is filled with the fill value. + * + * The behavior of the library for the various combinations of + * valid dataspace identifiers and #H5S_ALL for the \p mem_space_id + * and the \p file_space_id parameters is described below: + * + * <table> + * <tr> + * <th>mem_space_id</th> + * <th>file_space_id</th> + * <th>Behavior</th> + * </tr> + * <tr> + * <td>valid dataspace ID</td> + * <td>valid dataspace ID</td> + * <td>\p mem_space_id specifies the memory dataspace and the + * selection within it. \p file_space_id specifies the + * selection within the file dataset's dataspace.</td> + * </tr> + * <tr> + * <td>#H5S_ALL</td> + * <td>valid dataspace ID</td> + * <td>The file dataset's dataspace is used for the memory + * dataspace and the selection specified with \p file_space_id + * specifies the selection within it. The combination of the + * file dataset's dataspace and the selection from + * \p file_space_id is used for memory also.</td> + * </tr> + * <tr> + * <td>valid dataspace ID</td> + * <td>#H5S_ALL</td> + * <td>\p mem_space_id specifies the memory dataspace and the + * selection within it. The selection within the file + * dataset's dataspace is set to the "all" selection.</td> + * </tr> + * <tr> + * <td>#H5S_ALL</td> + * <td>#H5S_ALL</td> + * <td>The file dataset's dataspace is used for the memory + * dataspace and the selection within the memory dataspace + * is set to the "all" selection. The selection within the + * file dataset's dataspace is set to the "all" selection.</td> + * </tr> + * </table> + * + * \details Setting an #H5S_ALL selection indicates that the entire + * dataspace, as defined by the current dimensions of a dataspace, + * will be selected. The number of elements selected in the memory + * dataspace must match the number of elements selected in the + * file dataspace. + * + * \p dxpl_id can be the constant #H5P_DEFAULT, in which case the + * default data transfer properties are used. + * + */ +H5_DLL herr_t H5Dread(hid_t dset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, + hid_t dxpl_id, void *buf /*out*/); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Writes raw data from a buffer to a dataset + * + * \param[in] dset_id Identifier of the dataset to read from + * \param[in] mem_type_id Identifier of the memory datatype + * \param[in] mem_space_id Identifier of the memory dataspace + * \param[in] file_space_id Identifier of the dataset's dataspace in the file + * \dxpl_id + * \param[out] buf Buffer with data to be written to the file + * + * \return \herr_t + * + * \details H5Dwrite() writes a (partial) dataset, specified by + * its identifier \p dset_id, from the application memory buffer \p + * buf into the file. Data transfer properties are defined by the + * argument \p dxpl_id. The memory datatype of the (partial) + * dataset is identified by the identifier \p mem_type_id. The + * part of the dataset to write is defined by \p mem_space_id + * and \p file_space_id. + * + * If \p mem_type_id is either a fixed-length or variable-length + * string, it is important to set the string length when defining + * the datatype. String datatypes are derived from #H5T_C_S1 + * (or #H5T_FORTRAN_S1 for Fortran codes), which defaults + * to 1 character in size. See H5Tset_size() and Creating + * variable-length string datatypes. + * + * \p file_space_id is used to specify only the selection within + * the file dataset's dataspace. Any dataspace specified in \p + * file_space_id is ignored by the library and the dataset's + * dataspace is always used. \p file_space_id can be the constant + * #H5S_ALL, which indicates that the entire file dataspace, + * as defined by the current dimensions of the dataset, is to + * be selected. + * + * \p mem_space_id is used to specify both the memory dataspace + * and the selection within that dataspace. mem_space_id can be + * the constant #H5S_ALL, in which case the file dataspace is + * used for the memory dataspace and the selection defined with \p + * file_space_id is used for the selection within that dataspace. + * + * The behavior of the library for the various combinations of + * valid dataspace IDs and #H5S_ALL for the mem_space_id and + * thefile_space_id parameters is described below: + * + * <table> + * <tr><th>\c mem_space_id</th> + * <th>\c file_space_id</th> + * <th>Behavior</th></tr> + * <tr><td>valid dataspace ID</td> + * <td>valid dataspace ID</td> + * <td>\p mem_space_id specifies the memory dataspace and the + * selection within it. \p file_space_id specifies the + * selection within the file dataset's dataspace.</td></tr> + * <tr><td>#H5S_ALL</td> + * <td>valid dataspace ID</td> + * <td>The file dataset's dataspace is used for the memory + * dataspace and the selection specified with \p file_space_id + * specifies the selection within it. The combination of the + * file dataset's dataspace and the selection from \p + * file_space_id is used for memory also. valid dataspace + * ID</td></tr> + * <tr><td>valid dataspace ID</td> + * <td>#H5S_ALL</td> + * <td>\p mem_space_id specifies the memory dataspace and the + * selection within it. The selection within the file + * dataset's dataspace is set to "all" selection.</td></tr> + * <tr><td>#H5S_ALL</td> + * <td>#H5S_ALL</td> + * <td>The file dataset's dataspace is used for the memory + * dataspace and the selection within the memory dataspace is + * set to the "all" selection. The selection within the file + * dataset's dataspace is set to the "all" + * selection.</td></tr> + * </table> + * Setting an "all" selection indicates that the entire dataspace, + * as defined by the current dimensions of a dataspace, will + * be selected. The number of elements selected in the memory + * dataspace must match the number of elements selected in the + * file dataspace. + * + * \p dxpl_id can be the constant #H5P_DEFAULT, in which + * case the default data transfer properties are used. + * + * Writing to a dataset will fail if the HDF5 file was not opened + * with write access permissions. + * + * If the dataset's space allocation time is set to + * #H5D_ALLOC_TIME_LATE or #H5D_ALLOC_TIME_INCR and the space for + * the dataset has not yet been allocated, that space is allocated + * when the first raw data is written to the dataset. Unused space + * in the dataset will be written with fill values at the same + * time if the dataset's fill time is set to #H5D_FILL_TIME_IFSET + * or #H5D_FILL_TIME_ALLOC. + * + * \attention If a dataset's storage layout is 'compact', care must be + * taken when writing data to the dataset in parallel. A compact + * dataset's raw data is cached in memory and may be flushed + * to the file from any of the parallel processes, so parallel + * applications should always attempt to write identical data to + * the dataset from all processes. + * + * \see H5Pset_fill_time(), H5Pset_alloc_time() + * + */ +H5_DLL herr_t H5Dwrite(hid_t dset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, + hid_t dxpl_id, const void *buf); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Writes a raw data chunk from a buffer directly to a dataset in a file + * + * \dset_id + * \dxpl_id + * \param[in] filters Mask for identifying the filters in use + * \param[in] offset Logical position of the chunk’s first element in the + * dataspace + * \param[in] data_size Size of the actual data to be written in bytes + * \param[in] buf Buffer containing data to be written to the chunk + * + * \return \herr_t + * + * \details H5Dwrite_chunk() writes a raw data chunk as specified + * by its logical offset \p offset in a chunked dataset \p dset_id + * from the application memory buffer \p buf to the dataset in + * the file. Typically, the data in \p buf is preprocessed in + * memory by a custom transformation, such as compression. The + * chunk will bypass the library’s internal data transfer + * pipeline, including filters, and will be written directly to + * the file. Only one chunk can be written with this function. + * + * H5Dwrite_chunk() replaces the now deprecated H5DOwrite_chunk() + * function, which was located in the high level optimization + * library. The parameters and behavior are identical to the + * original. + * + * \p filters is a mask providing a record of which filters are + * used with the the chunk. The default value of the mask is + * zero (0), indicating that all enabled filters are applied. A + * filter is skipped if the bit corresponding to the filter’s + * position in the pipeline (0 ≤ position < 32) is turned on. + * This mask is saved with the chunk in the file. + * + * \p offset is an array specifying the logical position of the + * first element of the chunk in the dataset’s dataspace. The + * length of the offset array must equal the number of dimensions, + * or rank, of the dataspace. The values in offset must not exceed + * the dimension limits and must specify a point that falls on + * a dataset chunk boundary. + * + * \p data_size is the size in bytes of the chunk, representing + * the number of bytes to be read from the buffer \p buf. If the + * data chunk has been precompressed, \p data_size should be the + * size of the compressed data. + * + * \p buf is the memory buffer containing data to be written to + * the chunk in the file. + * + * \attention Exercise caution when using H5Dread_chunk() and + * H5Dwrite_chunk(), as they read and write data chunks directly + * in a file. H5Dwrite_chunk() bypasses hyperslab selection, the + * conversion of data from one datatype to another, and the filter + * pipeline to write the chunk. Developers should have experience + * with these processes before using this function. Please see + * Using the Direct Chunk Write Function for more information. + * + * \note H5Dread_chunk() and H5Dwrite_chunk() are not supported under + * parallel and do not support variable length types. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dwrite_chunk(hid_t dset_id, hid_t dxpl_id, uint32_t filters, const hsize_t *offset, + size_t data_size, const void *buf); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Reads a raw data chunk directly from a dataset in a file into + * a buffer + * + * \dset_id + * \dxpl_id + * \param[in] offset Logical position of the chunk’s first element in the + * dataspace + * \param[in,out] filters Mask for identifying the filters in use + * \param[out] buf Buffer containing data to be written to the chunk + * + * \return \herr_t + * + * \details H5Dread_chunk() reads a raw data chunk as specified by + * its logical offset \p offset in a chunked dataset \p dset_id + * from the dataset in the file into the application memory + * buffer \p buf. The data in \p buf is read directly from the + * file bypassing the library’s internal data transfer pipeline, + * including filters. + * + * \p offset is an array specifying the logical position of the + * first element of the chunk in the dataset’s dataspace. The + * length of the \p offset array must equal the number of dimensions, + * or rank, of the dataspace. The values in \p offset must not exceed + * the dimension limits and must specify a point that falls on + * a dataset chunk boundary. + * + * The mask \p filters indicates which filters are used with the + * chunk when written. A zero value indicates that all enabled + * filters are applied on the chunk. A filter is skipped if the + * bit corresponding to the filter’s position in the pipeline + * (0 ≤ position < 32) is turned on. + * + * \p buf is the memory buffer containing the chunk read from + * the dataset in the file. + * + * \attention Exercise caution when using H5Dread_chunk() and + * H5Dwrite_chunk(), as they read and write data chunks directly + * in a file. H5Dwrite_chunk() bypasses hyperslab selection, the + * conversion of data from one datatype to another, and the filter + * pipeline to write the chunk. Developers should have experience + * with these processes before using this function. Please see + * Using the Direct Chunk Write Function for more information. + * + * \note H5Dread_chunk() and H5Dwrite_chunk() are not supported under + * parallel and do not support variable length types. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dread_chunk(hid_t dset_id, hid_t dxpl_id, const hsize_t *offset, uint32_t *filters, + void *buf); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Iterates over all selected elements in a dataspace + * + * \param[in,out] buf Buffer containing the elements to iterate over + * \type_id + * \space_id + * \param[in] op Function pointer + * \param[in,out] operator_data User-defined data + * + * \return \success{The return value of the first operator that returns + * non-zero, or zero if all members were processed with no + * operator returning non-zero.} + * \return \failure{Negative if an error occurs in the library, or the negative + * value returned by one of the operators.} + * + * \details H5Diterate() iterates over all the data elements + * in the memory buffer \p buf, executing the callback function + * \p op once for each such data element. + * + * The prototype of the callback function \p op is as follows + * (as defined in the source code file H5Lpublic.h): + * \snippet this H5D_operator_t_snip + * The parameters of this callback function are: + * + * <table> + * <tr><td>\c elem</td> + * <td><tt>[in,out]</tt></td> + * <td>Pointer to the memory buffer containing the current + * data element</td></tr> + * <tr><td>\c type_id</td> + * <td><tt>[in]</tt></td> + * <td>Datatype identifier of the elements stored in elem</td></tr> + * <tr><td>\c ndim</td> + * <td><tt>[in]</tt></td> + * <td>Number of dimensions for the point array</td></tr> + * <tr><td>\c point</td> + * <td><tt>[in]</tt></td> + * <td>Array containing the location of the element within + * the original dataspace</td></tr> + * <tr><td>\c operator_data</td> + * <td><tt>[in,out]</tt></td> + * <td>Pointer to any user-defined data associated with the + * operation</td></tr> + * </table> + * + * The possible return values from the callback function, and + * the effect ofeach,are as follows: + * + * \li Zero causes the iterator to continue, returning zero + * when all data elements have been processed. + * \li A positive value causes the iterator to immediately + * return that positive value, indicating short-circuit success. + * \li A negative value causes the iterator to immediately return + * that value, indicating failure. + * + * The \p operator_data parameter is a user-defined pointer to + * the data required to process dataset elements in the course + * of the iteration. If operator needs to pass data back to the + * application, such data can be returned in this same buffer. This + * pointer is passed back to each step of the iteration in the + * operator callback function’s operator_data parameter. + * + * Unlike other HDF5 iterators, this iteration operation cannot + * be restarted at the point of exit; a second H5Diterate() + * call will always restart at the beginning. + * + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Diterate(void *buf, hid_t type_id, hid_t space_id, H5D_operator_t op, void *operator_data); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Determines the number of bytes required to store variable-length + * (VL) data + * + * \dset_id + * \type_id + * \space_id + * \param[out] size Size in bytes of the memory buffer required to store + * the VL data + * + * \return \herr_t + * + * \details H5Dvlen_get_buf_size() determines the number of bytes + * required to store the VL data from the dataset, using \p + * space_id for the selection in the dataset on disk and the \p + * type_id for the memory representation of the VL data in memory. + * \p size is returned with the number of bytes required to store + * the VL data in memory. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dvlen_get_buf_size(hid_t dset_id, hid_t type_id, hid_t space_id, hsize_t *size); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Fills dataspace elements with a fill value in a memory buffer + * + * \param[in] fill Pointer to the fill value to be used + * \param[in] fill_type_id Fill value datatype identifier + * \param[in,out] buf Pointer to the memory buffer containing the + * selection to be filled + * \param[in] buf_type_id Datatype of dataspace elements to be filled + * \space_id + * + * \return \herr_t + * + * \details H5Dfill() fills the dataspace selection in memory, \p space_id, + * with the fill value specified in \p fill. If \p fill is NULL, + * a fill value of 0 (zero) is used. + * + * \p fill_type_id specifies the datatype of the fill value. + * \p buf specifies the buffer in which the dataspace elements + * will be written. + * \p buf_type_id specifies the datatype of those data elements. + * + * \note Note that if the fill value datatype differs from the memory + * buffer datatype, the fill value will be converted to the memory + * buffer datatype before filling the selection. + * + * \note Applications sometimes write data only to portions of an + * allocated dataset. It is often useful in such cases to fill + * the unused space with a known fill value. See the following + * function for more information: + * - H5Pset_fill_value() + * - H5Pget_fill_value() + * - H5Pfill_value_defined() + * - H5Pset_fill_time() + * - H5Pget_fill_time() + * - H5Pcreate() + * - H5Pcreate_anon() + * + */ +H5_DLL herr_t H5Dfill(const void *fill, hid_t fill_type_id, void *buf, hid_t buf_type_id, hid_t space_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Changes the sizes of a dataset’s dimensions + * + * \dset_id + * \param[in] size[] Array containing the new magnitude of each dimension + * of the dataset + * + * \return \herr_t + * + * \details H5Dset_extent() sets the current dimensions of the + * chunked dataset \p dset_id to the sizes specified in size. + * + * \p size is a 1-dimensional array with n elements, where \p n is + * the rank of the dataset’s current dataspace. + * + * This function can be applied to the following datasets: + * - A chunked dataset with unlimited dimensions + * - A chunked dataset with fixed dimensions if the new dimension + * sizes are less than the maximum sizes set with maxdims (see + * H5Screate_simple()) + * - An external dataset with unlimited dimensions + * - An external dataset with fixed dimensions if the new dimension + * sizes are less than the maximum sizes set with \p maxdims + * + * Note that external datasets are always contiguous and can be + * extended only along the first dimension. + * + * Space on disk is immediately allocated for the new dataset extent if + * the dataset’s space allocation time is set to #H5D_ALLOC_TIME_EARLY. + * + * Fill values will be written to the dataset in either of the + * following situations, but not otherwise: + * + * - If the dataset’s fill time is set to #H5D_FILL_TIME_IFSET and a + * fill value is defined (see H5Pset_fill_time() and + * H5Pset_fill_value()) + * - If the dataset’s fill time is set to #H5D_FILL_TIME_ALLOC + * (see H5Pset_alloc_time()) + * + * \note + * \li If the sizes specified in \p size array are smaller than + * the dataset’s current dimension sizes, H5Dset_extent() will reduce + * the dataset’s dimension sizes to the specified values. It is the + * user application’s responsibility to ensure that valuable data is + * not lost as H5Dset_extent() does not check. + * + * \li Except for external datasets, H5Dset_extent() is for use with + * chunked datasets only, not contiguous datasets. + * + * \li A call to H5Dset_extent() affects the dataspace of a dataset. + * If a dataspace handle was opened for a dataset prior to a call to + * H5Dset_extent() then that dataspace handle will no longer reflect + * the correct dataspace extent of the dataset. H5Dget_space() must + * be called (after closing the previous handle) to obtain the current + * dataspace extent. + * + * \since 1.8.0 + * + */ +H5_DLL herr_t H5Dset_extent(hid_t dset_id, const hsize_t size[]); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Flushes all buffers associated with a dataset to disk + * + * \dset_id + * + * \return \herr_t + * + * \details H5Dflush() causes all buffers associated with a + * dataset to be immediately flushed to disk without removing + * the data from the cache. + * + * \note HDF5 does not possess full control over buffering. + * H5Dflush() flushes the internal HDF5 buffers and then asks the + * operating system (the OS) to flush the system buffers for the + * open files. After that, the OS is responsible for ensuring + * that the data is actually flushed to disk. + * + */ +H5_DLL herr_t H5Dflush(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Refreshes all buffers associated with a dataset + * + * \dset_id + * + * \return \herr_t + * + * \details H5Drefresh() causes all buffers associated with a + * dataset to be cleared and immediately re-loaded with updated + * contents from disk. + * + * This function essentially closes the dataset, evicts all + * metadata associated with it from the cache, and then re-opens + * the dataset. The reopened dataset is automatically re-registered + * with the same identifier. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Drefresh(hid_t dset_id); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Scatters data into a selection within a memory buffer + * + * \param[in] op Callback function which provides data to be scattered + * \param[in] op_data User-defined pointer to data required by op + * \param[in] type_id Identifier for the datatype describing the data in + * both the source and destination buffers + * \param[in] dst_space_id Identifier for the dataspace for destination + * \param[out] dst_buf Destination buffer which the data will be scattered to + * + * \return \herr_t + * + * \details H5Dscatter() retrieves data from the supplied callback + * \p op and scatters it to the supplied buffer \p dst_buf in a + * manner similar to data being written to a dataset. + * + * \p dst_space_id is a dataspace which defines the extent of \p + * dst_buf and the selection within it to scatter the data to. + * + * \p type_id is the datatype of the data to be scattered in both + * the source and destination buffers. + * + * \p dst_buf must be at least as large as the number of elements + * in the extent of \p dst_space_id times the size in bytes of + * \p type_id. + * + * To retrieve the data to be scattered, H5Dscatter() repeatedly + * calls \p op, which should return a valid source buffer, until + * enough data to fill the selection has been retrieved. The + * prototype of the callback function \p op is as follows (as + * defined in the source code file H5Dpublic.h): + * \snippet this H5D_scatter_func_t_snip + * The parameters of this callback function are described below: + * + * <table> + * <tr><td>\c src_buf</td> + * <td><tt>[out]</tt></td> + * <td>Pointer to the buffer holding the next set of elements to + * scatter. On entry, the value of where \c src_buf points to + * is undefined. The callback function should set \c src_buf + * to point to the next set of elements.</td></tr> + * <tr><td>\c src_buf_bytes_used</td> + * <td><tt>[out]</tt></td> + * <td>Pointer to the number of valid bytes in \c src_buf. On + * entry, the value where \c src_buf_bytes_used points to is + * undefined. The callback function should set + * \c src_buf_bytes_used to the of valid bytes in \c src_buf. + * This number must be a multiple of the datatype size. + * </td></tr> + * <tr><td>\c op_data</td> + * <td><tt>[in,out]</tt></td> + * <td>User-defined pointer to data required by the callback + * function. A pass-through of the \c op_data pointer provided + * with the H5Dscatter() function call.</td></tr> + * </table> + * + * The callback function should always return at least one + * element in \p src_buf, and must not return more elements + * than are remaining to be scattered. This function will be + * repeatedly called until all elements to be scattered have + * been returned. The callback function should return zero (0) + * to indicate success, and a negative value to indicate failure. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dscatter(H5D_scatter_func_t op, void *op_data, hid_t type_id, hid_t dst_space_id, + void *dst_buf); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Gathers data from a selection within a memory buffer + * raw data chunk in a dataset + * + * \param[in] src_space_id Dataspace identifier for the source buffer + * \param[in] src_buf Source buffer which the data will be gathered from + * \param[in] type_id Datatype identifier for the source + * \param[in] dst_buf_size Size in bytes of \p dst_buf + * \param[out] dst_buf Destination buffer for the gathered data + * \param[in] op Callback function which handles the gathered data + * \param[in] op_data User-defined pointer to data required by \p op + * + * \return \herr_t + * + * \details H5Dgather() retrieves data from a selection within the supplied + * buffer src_buf and passes it to the supplied callback function + * \p op in a contiguous form. + * + * The dataspace \p src_space_id describes both the dimensions of + * the source buffer and the selection within the source buffer + * to gather data from. + * + * \p src_buf must be at least the size of the gathered data, that + * is, the number of elements in the extent of \p src_space_id + * times the size in bytes of \p type_id. + * + * The datatype \p type_id describes the data in both the source + * and destination buffers. This information is used to calculate + * the element size. + * + * The data is gathered into \p dst_buf, which needs to be large + * enough to hold all the data if the callback function \p op is + * not provided. + * + * \p op is a callback function which handles the gathered data. + * It is optional if \p dst_buf is large enough to hold all of the + * gathered data; required otherwise. + * + * If no callback function is provided, H5Dgather() simply gathers + * the data into \p dst_buf and returns. If a callback function is + * provided, H5Dgather() repeatedly gathers up to \p dst_buf_size + * bytes to process the serialized data. The prototype of the + * callback function \p op is as follows (as defined in the source + * code file H5Dpublic.h): + * \snippet this H5D_gather_func_t_snip + * The parameters of this callback function are described in the + * table below. + * <table> + * <tr><td>\c dst_buf</td> + * <td>Pointer to the destination buffer which has been filled + * with the next set of elements gathered. This will always be + * identical to the \p dst_buf passed to H5Dgather().</td></tr> + * <tr><td>\c dst_buf_bytes_used</td> + * <td>Pointer to the number of valid bytes in \p dst_buf. + * This number must be a multiple of the datatype + * size.</td></tr> + * <tr><td>\c op_data</td> + * <td>User-defined pointer to data required by the callback + * function; a pass-through of the \p op_data pointer + * provided with the H5Dgather() function call.</td></tr> + * </table> + * The callback function should process, store, or otherwise, + * make use of the data returned in \p dst_buf before it returns, + * because the buffer will be overwritten unless it is the last + * call to the callback. This function will be repeatedly called + * until all gathered elements have been passed to the callback + * in \p dst_buf. The callback function should return zero (0) + * to indicate success, and a negative value to indicate failure. + * + * \since 1.10.2 + * + */ +H5_DLL herr_t H5Dgather(hid_t src_space_id, const void *src_buf, hid_t type_id, size_t dst_buf_size, + void *dst_buf, H5D_gather_func_t op, void *op_data); + +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Closes the specified dataset + * + * \dset_id + * + * \return \herr_t + * + * \details H5Dclose() ends access to a dataset specified by \p dset_id + * and releases resources used by it. + * + * \attention Further use of a released dataset identifier is illegal; a + * function using such an identifier will generate an error. + * + * \since 1.8.0 + * + * \see H5Dcreate2(), H5Dopen2() + * + */ +H5_DLL herr_t H5Dclose(hid_t dset_id); /* Internal API routines */ +H5_DLL herr_t H5Ddebug(hid_t dset_id); H5_DLL herr_t H5Dformat_convert(hid_t dset_id); H5_DLL herr_t H5Dget_chunk_index_type(hid_t did, H5D_chunk_index_t *idx_type); @@ -194,10 +1462,182 @@ H5_DLL herr_t H5Dget_chunk_index_type(hid_t did, H5D_chunk_index_t *idx_type); /* Typedefs */ /* Function prototypes */ -H5_DLL hid_t H5Dcreate1(hid_t file_id, const char *name, hid_t type_id, hid_t space_id, hid_t dcpl_id); -H5_DLL hid_t H5Dopen1(hid_t file_id, const char *name); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Creates a dataset at the specified location + * + * \fgdta_loc_id + * \param[in] name Name of the dataset to create + * \type_id + * \space_id + * \dcpl_id + * + * \return \hid_t{dataset} + * + * \deprecated This function is deprecated in favor of the function H5Dcreate2() + * or the macro H5Dcreate(). + * + * \details H5Dcreate1() creates a data set with a name, \p name, in the + * location specified by the identifier \p loc_id. \p loc_id may be a + * file, group, dataset, named datatype or attribute. If an attribute, + * dataset, or named datatype is specified for \p loc_id then the + * dataset will be created at the location where the attribute, + * dataset, or named datatype is attached. + * + * \p name can be a relative path based at \p loc_id or an absolute + * path from the root of the file. Use of this function requires that + * any intermediate groups specified in the path already exist. + * + * The dataset’s datatype and dataspace are specified by \p type_id and + * \p space_id, respectively. These are the datatype and dataspace of + * the dataset as it will exist in the file, which may differ from the + * datatype and dataspace in application memory. + * + * Names within a group are unique: H5Dcreate1() will return an error + * if a link with the name specified in name already exists at the + * location specified in \p loc_id. + * + * As is the case for any object in a group, the length of a dataset + * name is not limited. + * + * \p dcpl_id is an #H5P_DATASET_CREATE property list created with \p + * H5reate1() and initialized with various property list functions + * described in Property List Interface. + * + * H5Dcreate() and H5Dcreate_anon() return an error if the dataset’s + * datatype includes a variable-length (VL) datatype and the fill value + * is undefined, i.e., set to \c NULL in the dataset creation property + * list. Such a VL datatype may be directly included, indirectly + * included as part of a compound or array datatype, or indirectly + * included as part of a nested compound or array datatype. + * + * H5Dcreate() and H5Dcreate_anon() return a dataset identifier for + * success or a negative value for failure. The dataset identifier + * should eventually be closed by calling H5Dclose() to release + * resources it uses. + * + * See H5Dcreate_anon() for discussion of the differences between + * H5Dcreate() and H5Dcreate_anon(). + * + * The HDF5 library provides flexible means of specifying a fill value, + * of specifying when space will be allocated for a dataset, and of + * specifying when fill values will be written to a dataset. + * + * \version 1.8.0 Function H5Dcreate() renamed to H5Dcreate1() and deprecated in this release. + * \since 1.0.0 + * + * \see H5Dopen2(), H5Dclose(), H5Tset_size() + * + */ +H5_DLL hid_t H5Dcreate1(hid_t loc_id, const char *name, hid_t type_id, hid_t space_id, hid_t dcpl_id); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Opens an existing dataset + * + * \fgdta_loc_id + * \param[in] name Name of the dataset to access + * + * \return \hid_t{dataset} + * + * \deprecated This function is deprecated in favor of the function H5Dopen2() + * or the macro H5Dopen(). + * + * \details H5Dopen1() opens an existing dataset for access at the location + * specified by \p loc_id. \p loc_id may be a file, group, dataset, + * named datatype or attribute. If an attribute, dataset, or named + * datatype is specified for loc_id then the dataset will be opened at + * the location where the attribute, dataset, or named datatype is + * attached. name is a dataset name and is used to identify the dataset + * in the file. + * + * A dataset opened with this function should be closed with H5Dclose() + * when the dataset is no longer needed so that resource leaks will not + * develop. + * + * \version 1.8.0 Function H5Dopen() renamed to H5Dopen1() and deprecated in this release. + * \since 1.0.0 + * + */ +H5_DLL hid_t H5Dopen1(hid_t loc_id, const char *name); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Extends a dataset + * + * \dset_id + * \param[in] size Array containing the new size of each dimension + * + * \return \herr_t + * + * \deprecated This function is deprecated in favor of the function H5Dset_extent(). + * + * \details H5Dextend() verifies that the dataset is at least of size \p size, + * extending it if necessary. The dimensionality of size is the same as + * that of the dataspace of the dataset being changed. + * + * This function can be applied to the following datasets: + * \li Any dataset with unlimited dimensions + * \li A dataset with fixed dimensions if the current dimension sizes + * are less than the maximum sizes set with \c maxdims + * (see H5Screate_simple()) + * + * Space on disk is immediately allocated for the new dataset extent if + * the dataset’s space allocation time is set to + * #H5D_ALLOC_TIME_EARLY. Fill values will be written to the dataset if + * the dataset’s fill time is set to #H5D_FILL_TIME_IFSET or + * #H5D_FILL_TIME_ALLOC. (See H5Pset_fill_time() and + * H5Pset_alloc_time().) + * + * This function ensures that the dataset dimensions are of at least + * the sizes specified in size. The function H5Dset_extent() must be + * used if the dataset dimension sizes are are to be reduced. + * + * \version 1.8.0 Function Function deprecated in this release. Parameter size + * syntax changed to \Code{const hsize_t size[]} in this release. + * + */ H5_DLL herr_t H5Dextend(hid_t dset_id, const hsize_t size[]); -H5_DLL herr_t H5Dvlen_reclaim(hid_t type_id, hid_t space_id, hid_t plist_id, void *buf); +/** + * -------------------------------------------------------------------------- + * \ingroup H5D + * + * \brief Reclaims variable-length (VL) datatype memory buffers + * + * \type_id + * \space_id + * \dxpl_id + * \param[in] buf Pointer to the buffer to be reclaimed + * + * \return \herr_t + * + * \deprecated This function has been deprecated in HDF5-1.12 in favor of the + * function H5Treclaim(). + * + * \details H5Dvlen_reclaim() reclaims memory buffers created to store VL + * datatypes. + * + * The \p type_id must be the datatype stored in the buffer. The \p + * space_id describes the selection for the memory buffer to free the + * VL datatypes within. The \p dxpl_id is the dataset transfer property + * list which was used for the I/O transfer to create the buffer. And + * \p buf is the pointer to the buffer to be reclaimed. + * + * The VL structures (\ref hvl_t) in the user's buffer are modified to + * zero out the VL information after the memory has been reclaimed. + * + * If nested VL datatypes were used to create the buffer, this routine + * frees them from the bottom up, releasing all the memory without + * creating memory leaks. + * + * \version 1.12.0 Routine was deprecated + * + */ +H5_DLL herr_t H5Dvlen_reclaim(hid_t type_id, hid_t space_id, hid_t dxpl_id, void *buf); #endif /* H5_NO_DEPRECATED_SYMBOLS */ diff --git a/src/H5Dscatgath.c b/src/H5Dscatgath.c index 34f35cd..971ddfb 100644 --- a/src/H5Dscatgath.c +++ b/src/H5Dscatgath.c @@ -898,198 +898,3 @@ H5D__compound_opt_write(size_t nelmts, const H5D_type_info_t *type_info) FUNC_LEAVE_NOAPI(SUCCEED) } /* end H5D__compound_opt_write() */ - -/*------------------------------------------------------------------------- - * Function: H5Dscatter - * - * Purpose: Scatters data provided by the callback op to the - * destination buffer dst_buf, where the dimensions of - * dst_buf and the selection to be scattered to are specified - * by the dataspace dst_space_id. The type of the data to be - * scattered is specified by type_id. - * - * Return: Non-negative on success/Negative on failure - * - * Programmer: Neil Fortner - * 14 Jan 2013 - * - *------------------------------------------------------------------------- - */ -herr_t -H5Dscatter(H5D_scatter_func_t op, void *op_data, hid_t type_id, hid_t dst_space_id, void *dst_buf) -{ - H5T_t * type; /* Datatype */ - H5S_t * dst_space; /* Dataspace */ - H5S_sel_iter_t *iter = NULL; /* Selection iteration info*/ - hbool_t iter_init = FALSE; /* Selection iteration info has been initialized */ - const void * src_buf = NULL; /* Source (contiguous) data buffer */ - size_t src_buf_nbytes = 0; /* Size of src_buf */ - size_t type_size; /* Datatype element size */ - hssize_t nelmts; /* Number of remaining elements in selection */ - size_t nelmts_scatter = 0; /* Number of elements to scatter to dst_buf */ - herr_t ret_value = SUCCEED; /* Return value */ - - FUNC_ENTER_API(FAIL) - H5TRACE5("e", "DS*xii*x", op, op_data, type_id, dst_space_id, dst_buf); - - /* Check args */ - if (op == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid callback function pointer") - if (NULL == (type = (H5T_t *)H5I_object_verify(type_id, H5I_DATATYPE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a datatype") - if (NULL == (dst_space = (H5S_t *)H5I_object_verify(dst_space_id, H5I_DATASPACE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") - if (dst_buf == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no destination buffer provided") - - /* Get datatype element size */ - if (0 == (type_size = H5T_GET_SIZE(type))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get datatype size") - - /* Get number of elements in dataspace */ - if ((nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(dst_space)) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") - - /* Allocate the selection iterator */ - if (NULL == (iter = H5FL_MALLOC(H5S_sel_iter_t))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTALLOC, FAIL, "can't allocate selection iterator") - - /* Initialize selection iterator */ - if (H5S_select_iter_init(iter, dst_space, type_size, 0) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to initialize selection iterator information") - iter_init = TRUE; - - /* Loop until all data has been scattered */ - while (nelmts > 0) { - /* Make callback to retrieve data */ - if (op(&src_buf, &src_buf_nbytes, op_data) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CALLBACK, FAIL, "callback operator returned failure") - - /* Calculate number of elements */ - nelmts_scatter = src_buf_nbytes / type_size; - - /* Check callback results */ - if (!src_buf) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback did not return a buffer") - if (src_buf_nbytes == 0) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback returned a buffer size of 0") - if (src_buf_nbytes % type_size) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "buffer size is not a multiple of datatype size") - if (nelmts_scatter > (size_t)nelmts) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "callback returned more elements than in selection") - - /* Scatter data */ - if (H5D__scatter_mem(src_buf, iter, nelmts_scatter, dst_buf) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "scatter failed") - - nelmts -= (hssize_t)nelmts_scatter; - } /* end while */ - -done: - /* Release selection iterator */ - if (iter_init && H5S_SELECT_ITER_RELEASE(iter) < 0) - HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "Can't release selection iterator") - if (iter) - iter = H5FL_FREE(H5S_sel_iter_t, iter); - - FUNC_LEAVE_API(ret_value) -} /* H5Dscatter() */ - -/*------------------------------------------------------------------------- - * Function: H5Dgather - * - * Purpose: Gathers data provided from the source buffer src_buf to - * contiguous buffer dst_buf, then calls the callback op. - * The dimensions of src_buf and the selection to be gathered - * are specified by the dataspace src_space_id. The type of - * the data to be gathered is specified by type_id. - * - * Return: Non-negative on success/Negative on failure - * - * Programmer: Neil Fortner - * 16 Jan 2013 - * - *------------------------------------------------------------------------- - */ -herr_t -H5Dgather(hid_t src_space_id, const void *src_buf, hid_t type_id, size_t dst_buf_size, void *dst_buf, - H5D_gather_func_t op, void *op_data) -{ - H5T_t * type; /* Datatype */ - H5S_t * src_space; /* Dataspace */ - H5S_sel_iter_t *iter = NULL; /* Selection iteration info*/ - hbool_t iter_init = FALSE; /* Selection iteration info has been initialized */ - size_t type_size; /* Datatype element size */ - hssize_t nelmts; /* Number of remaining elements in selection */ - size_t dst_buf_nelmts; /* Number of elements that can fit in dst_buf */ - size_t nelmts_gathered; /* Number of elements gathered from src_buf */ - herr_t ret_value = SUCCEED; /* Return value */ - - FUNC_ENTER_API(FAIL) - H5TRACE7("e", "i*xiz*xDg*x", src_space_id, src_buf, type_id, dst_buf_size, dst_buf, op, op_data); - - /* Check args */ - if (NULL == (src_space = (H5S_t *)H5I_object_verify(src_space_id, H5I_DATASPACE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataspace") - if (src_buf == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no source buffer provided") - if (NULL == (type = (H5T_t *)H5I_object_verify(type_id, H5I_DATATYPE))) - HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a datatype") - if (dst_buf_size == 0) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "destination buffer size is 0") - if (dst_buf == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no destination buffer provided") - - /* Get datatype element size */ - if (0 == (type_size = H5T_GET_SIZE(type))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get datatype size") - - /* Get number of elements in dst_buf_size */ - dst_buf_nelmts = dst_buf_size / type_size; - if (dst_buf_nelmts == 0) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, - "destination buffer is not large enough to hold one element") - - /* Get number of elements in dataspace */ - if ((nelmts = (hssize_t)H5S_GET_SELECT_NPOINTS(src_space)) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTCOUNT, FAIL, "unable to get number of elements in selection") - - /* If dst_buf is not large enough to hold all the elements, make sure there - * is a callback */ - if (((size_t)nelmts > dst_buf_nelmts) && (op == NULL)) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no callback supplied and destination buffer too small") - - /* Allocate the selection iterator */ - if (NULL == (iter = H5FL_MALLOC(H5S_sel_iter_t))) - HGOTO_ERROR(H5E_DATASET, H5E_CANTALLOC, FAIL, "can't allocate selection iterator") - - /* Initialize selection iterator */ - if (H5S_select_iter_init(iter, src_space, type_size, 0) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "unable to initialize selection iterator information") - iter_init = TRUE; - - /* Loop until all data has been scattered */ - while (nelmts > 0) { - /* Gather data */ - if (0 == - (nelmts_gathered = H5D__gather_mem(src_buf, iter, MIN(dst_buf_nelmts, (size_t)nelmts), dst_buf))) - HGOTO_ERROR(H5E_IO, H5E_CANTCOPY, FAIL, "gather failed") - HDassert(nelmts_gathered == MIN(dst_buf_nelmts, (size_t)nelmts)); - - /* Make callback to process dst_buf */ - if (op && op(dst_buf, nelmts_gathered * type_size, op_data) < 0) - HGOTO_ERROR(H5E_DATASET, H5E_CALLBACK, FAIL, "callback operator returned failure") - - nelmts -= (hssize_t)nelmts_gathered; - HDassert(op || (nelmts == 0)); - } /* end while */ - -done: - /* Release selection iterator */ - if (iter_init && H5S_SELECT_ITER_RELEASE(iter) < 0) - HDONE_ERROR(H5E_DATASET, H5E_CANTFREE, FAIL, "Can't release selection iterator") - if (iter) - iter = H5FL_FREE(H5S_sel_iter_t, iter); - - FUNC_LEAVE_API(ret_value) -} /* H5Dgather() */ @@ -44,6 +44,7 @@ /********************/ /* Local Prototypes */ /********************/ +static herr_t H5S__close_cb(void *space, void **request); static htri_t H5S__is_simple(const H5S_t *sdim); /*****************************/ @@ -81,23 +82,44 @@ H5FL_ARR_DEFINE(hsize_t, H5S_MAX_RANK); /* Dataspace ID class */ static const H5I_class_t H5I_DATASPACE_CLS[1] = {{ - H5I_DATASPACE, /* ID class value */ - 0, /* Class flags */ - 2, /* # of reserved IDs for class */ - (H5I_free_t)H5S_close /* Callback routine for closing objects of this class */ + H5I_DATASPACE, /* ID class value */ + 0, /* Class flags */ + 2, /* # of reserved IDs for class */ + (H5I_free_t)H5S__close_cb /* Callback routine for closing objects of this class */ }}; /* Dataspace selection iterator ID class */ static const H5I_class_t H5I_SPACE_SEL_ITER_CLS[1] = {{ - H5I_SPACE_SEL_ITER, /* ID class value */ - 0, /* Class flags */ - 0, /* # of reserved IDs for class */ - (H5I_free_t)H5S_sel_iter_close /* Callback routine for closing objects of this class */ + H5I_SPACE_SEL_ITER, /* ID class value */ + 0, /* Class flags */ + 0, /* # of reserved IDs for class */ + (H5I_free_t)H5S__sel_iter_close_cb /* Callback routine for closing objects of this class */ }}; /* Flag indicating "top" of interface has been initialized */ static hbool_t H5S_top_package_initialize_s = FALSE; +/*------------------------------------------------------------------------- + * Function: H5S_init + * + * Purpose: Initialize the interface from some other layer. + * + * Return: Success: non-negative + * Failure: negative + *------------------------------------------------------------------------- + */ +herr_t +H5S_init(void) +{ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(FAIL) + /* FUNC_ENTER() does all the work */ + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S_init() */ + /*-------------------------------------------------------------------------- NAME H5S__init_package -- Initialize interface-specific information @@ -222,6 +244,37 @@ H5S_term_package(void) FUNC_LEAVE_NOAPI(n) } /* end H5S_term_package() */ +/*------------------------------------------------------------------------- + * Function: H5S__close_cb + * + * Purpose: Called when the ref count reaches zero on a dataspace's ID + * + * Return: SUCCEED / FAIL + * + * Programmer: Quincey Koziol + * Wednesday, April 8, 2020 + * + *------------------------------------------------------------------------- + */ +static herr_t +H5S__close_cb(void *_space, void H5_ATTR_UNUSED **request) +{ + H5S_t *space = (H5S_t *)_space; /* The dataspace to close */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_STATIC + + /* Sanity check */ + HDassert(space); + + /* Close the dataspace object */ + if (H5S_close(space) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CLOSEERROR, FAIL, "unable to close dataspace"); + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S__close_cb() */ + /*-------------------------------------------------------------------------- NAME H5S_get_validiated_dataspace diff --git a/src/H5Shyper.c b/src/H5Shyper.c index 307ded9..e12ff93 100644 --- a/src/H5Shyper.c +++ b/src/H5Shyper.c @@ -10297,7 +10297,7 @@ done: REVISION LOG --------------------------------------------------------------------------*/ herr_t -H5S_combine_hyperslab(H5S_t *old_space, H5S_seloper_t op, const hsize_t start[], const hsize_t *stride, +H5S_combine_hyperslab(const H5S_t *old_space, H5S_seloper_t op, const hsize_t start[], const hsize_t *stride, const hsize_t count[], const hsize_t *block, H5S_t **new_space) { unsigned u; /* Local index variable */ diff --git a/src/H5Smpio.c b/src/H5Smpio.c index 79eb64e..9a38aaa 100644 --- a/src/H5Smpio.c +++ b/src/H5Smpio.c @@ -697,8 +697,10 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new #ifdef H5S_DEBUG if (H5DEBUG(S)) { - HDfprintf(H5DEBUG(S), "%s: start=%Hd stride=%Hu count=%Hu block=%Hu xtent=%Hu", FUNC, - d[u].start, d[u].strid, d[u].count, d[u].block, d[u].xtent); + HDfprintf(H5DEBUG(S), + "%s: start=%" PRIdHSIZE " stride=%" PRIuHSIZE " count=%" PRIuHSIZE + " block=%" PRIuHSIZE " xtent=%" PRIuHSIZE, + FUNC, d[u].start, d[u].strid, d[u].count, d[u].block, d[u].xtent); if (u == 0) HDfprintf(H5DEBUG(S), " rank=%u\n", rank); else @@ -729,8 +731,10 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new #ifdef H5S_DEBUG if (H5DEBUG(S)) { - HDfprintf(H5DEBUG(S), "%s: start=%Hd stride=%Hu count=%Hu block=%Hu xtent=%Hu", FUNC, - d[u].start, d[u].strid, d[u].count, d[u].block, d[u].xtent); + HDfprintf(H5DEBUG(S), + "%s: start=%" PRIdHSIZE " stride=%" PRIuHSIZE " count=%" PRIuHSIZE + " block=%" PRIuHSIZE " xtent=%" PRIuHSIZE, + FUNC, d[u].start, d[u].strid, d[u].count, d[u].block, d[u].xtent); if (u == 0) HDfprintf(H5DEBUG(S), " rank=%u\n", rank); else @@ -754,7 +758,8 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new #ifdef H5S_DEBUG if (H5DEBUG(S)) { i = ((int)rank) - 1; - HDfprintf(H5DEBUG(S), " offset[%2d]=%Hu; max_xtent[%2d]=%Hu\n", i, offset[i], i, max_xtent[i]); + HDfprintf(H5DEBUG(S), " offset[%2d]=%" PRIuHSIZE "; max_xtent[%2d]=%" PRIuHSIZE "\n", i, offset[i], i, + max_xtent[i]); } #endif for (i = ((int)rank) - 2; i >= 0; --i) { @@ -762,7 +767,8 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new max_xtent[i] = max_xtent[i + 1] * d[i].xtent; #ifdef H5S_DEBUG if (H5DEBUG(S)) - HDfprintf(H5DEBUG(S), " offset[%2d]=%Hu; max_xtent[%2d]=%Hu\n", i, offset[i], i, max_xtent[i]); + HDfprintf(H5DEBUG(S), " offset[%2d]=%" PRIuHSIZE "; max_xtent[%2d]=%" PRIuHSIZE "\n", i, + offset[i], i, max_xtent[i]); #endif } /* end for */ @@ -777,9 +783,9 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new *******************************************************/ #ifdef H5S_DEBUG if (H5DEBUG(S)) { - HDfprintf(H5DEBUG(S), "%s: Making contig type %Zu MPI_BYTEs\n", FUNC, elmt_size); + HDfprintf(H5DEBUG(S), "%s: Making contig type %zu MPI_BYTEs\n", FUNC, elmt_size); for (i = ((int)rank) - 1; i >= 0; --i) - HDfprintf(H5DEBUG(S), "d[%d].xtent=%Hu \n", i, d[i].xtent); + HDfprintf(H5DEBUG(S), "d[%d].xtent=%" PRIuHSIZE "\n", i, d[i].xtent); } #endif @@ -809,7 +815,8 @@ H5S__mpio_reg_hyper_type(const H5S_t *space, size_t elmt_size, MPI_Datatype *new if (H5DEBUG(S)) HDfprintf(H5DEBUG(S), "%s: Dimension i=%d \n" - "start=%Hd count=%Hu block=%Hu stride=%Hu, xtent=%Hu max_xtent=%d\n", + "start=%" PRIdHSIZE " count=%" PRIuHSIZE " block=%" PRIuHSIZE " stride=%" PRIuHSIZE + ", xtent=%" PRIuHSIZE " max_xtent=%" PRIuHSIZE "\n", FUNC, i, d[i].start, d[i].count, d[i].block, d[i].strid, d[i].xtent, max_xtent[i]); #endif @@ -950,7 +957,8 @@ done: #ifdef H5S_DEBUG if (H5DEBUG(S)) - HDfprintf(H5DEBUG(S), "Leave %s, count=%ld is_derived_type=%t\n", FUNC, *count, *is_derived_type); + HDfprintf(H5DEBUG(S), "Leave %s, count=%d is_derived_type=%s\n", FUNC, *count, + (*is_derived_type) ? "TRUE" : "FALSE"); #endif FUNC_LEAVE_NOAPI(ret_value) } /* end H5S__mpio_reg_hyper_type() */ diff --git a/src/H5Snone.c b/src/H5Snone.c index 58f7b41..82e513e 100644 --- a/src/H5Snone.c +++ b/src/H5Snone.c @@ -12,7 +12,7 @@ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ /* - * Programmer: Quincey Koziol <koziol@ncsa.uiuc.edu> + * Programmer: Quincey Koziol * Tuesday, November 10, 1998 * * Purpose: "None" selection dataspace I/O functions. diff --git a/src/H5Spkg.h b/src/H5Spkg.h index a600c5d..c89b616 100644 --- a/src/H5Spkg.h +++ b/src/H5Spkg.h @@ -137,6 +137,11 @@ struct H5S_pnt_list_t { H5S_pnt_node_t *head; /* Pointer to head of point list */ H5S_pnt_node_t *tail; /* Pointer to tail of point list */ + + hsize_t last_idx; /* Index of the point after the last returned from H5S__get_select_elem_pointlist() */ + H5S_pnt_node_t *last_idx_pnt; /* Point after the last returned from H5S__get_select_elem_pointlist(). + * If we ever add a way to remove points or add points in the middle of + * the pointlist we will need to invalidate these fields. */ }; /* Information about hyperslab spans */ @@ -404,6 +409,9 @@ H5_DLL herr_t H5S__hyper_project_intersection(const H5S_t *src_space, const H5 const H5S_t *src_intersect_space, H5S_t *proj_space, hbool_t share_space); +/* Operations on selection iterators */ +H5_DLL herr_t H5S__sel_iter_close_cb(H5S_sel_iter_t *_sel_iter, void **request); + /* Testing functions */ #ifdef H5S_TESTING H5_DLL herr_t H5S__get_rebuild_status_test(hid_t space_id, H5S_diminfo_valid_t *status1, diff --git a/src/H5Spoint.c b/src/H5Spoint.c index 21ef966..5991116 100644 --- a/src/H5Spoint.c +++ b/src/H5Spoint.c @@ -238,7 +238,7 @@ H5S__point_iter_coords(const H5S_sel_iter_t *iter, hsize_t *coords) } /* end H5S__point_iter_coords() */ /*------------------------------------------------------------------------- - * Function: H5S_point_iter_block + * Function: H5S__point_iter_block * * Purpose: Retrieve the current block of iterator for current * selection @@ -843,6 +843,10 @@ H5S__copy_pnt_list(const H5S_pnt_list_t *src, unsigned rank) H5MM_memcpy(dst->high_bounds, src->high_bounds, (rank * sizeof(hsize_t))); H5MM_memcpy(dst->low_bounds, src->low_bounds, (rank * sizeof(hsize_t))); + /* Clear cached iteration point */ + dst->last_idx = 0; + dst->last_idx_pnt = NULL; + /* Set return value */ ret_value = dst; @@ -1511,8 +1515,9 @@ done: static herr_t H5S__get_select_elem_pointlist(const H5S_t *space, hsize_t startpoint, hsize_t numpoints, hsize_t *buf) { - H5S_pnt_node_t *node; /* Point node */ - unsigned rank; /* Dataspace rank */ + const hsize_t endpoint = startpoint + numpoints; /* Index of last point in iteration */ + H5S_pnt_node_t *node; /* Point node */ + unsigned rank; /* Dataspace rank */ FUNC_ENTER_STATIC_NOERR @@ -1522,14 +1527,20 @@ H5S__get_select_elem_pointlist(const H5S_t *space, hsize_t startpoint, hsize_t n /* Get the dataspace extent rank */ rank = space->extent.rank; - /* Get the head of the point list */ - node = space->select.sel_info.pnt_lst->head; + /* Check for cached point at the correct index */ + if (space->select.sel_info.pnt_lst->last_idx_pnt && + startpoint == space->select.sel_info.pnt_lst->last_idx) + node = space->select.sel_info.pnt_lst->last_idx_pnt; + else { + /* Get the head of the point list */ + node = space->select.sel_info.pnt_lst->head; - /* Iterate to the first point to return */ - while (node != NULL && startpoint > 0) { - startpoint--; - node = node->next; - } /* end while */ + /* Iterate to the first point to return */ + while (node != NULL && startpoint > 0) { + startpoint--; + node = node->next; + } /* end while */ + } /* end else */ /* Iterate through the node, copying each point's information */ while (node != NULL && numpoints > 0) { @@ -1539,6 +1550,10 @@ H5S__get_select_elem_pointlist(const H5S_t *space, hsize_t startpoint, hsize_t n node = node->next; } /* end while */ + /* Cached next point in iteration */ + space->select.sel_info.pnt_lst->last_idx = endpoint; + space->select.sel_info.pnt_lst->last_idx_pnt = node; + FUNC_LEAVE_NOAPI(SUCCEED) } /* end H5S__get_select_elem_pointlist() */ @@ -1572,13 +1587,14 @@ H5S__get_select_elem_pointlist(const H5S_t *space, hsize_t startpoint, hsize_t n REVISION LOG --------------------------------------------------------------------------*/ herr_t -H5Sget_select_elem_pointlist(hid_t spaceid, hsize_t startpoint, hsize_t numpoints, hsize_t buf[/*numpoints*/]) +H5Sget_select_elem_pointlist(hid_t spaceid, hsize_t startpoint, hsize_t numpoints, + hsize_t buf[/*numpoints*/] /*out*/) { H5S_t *space; /* Dataspace to modify selection of */ herr_t ret_value; /* return value */ FUNC_ENTER_API(FAIL) - H5TRACE4("e", "ihh*[a2]h", spaceid, startpoint, numpoints, buf); + H5TRACE4("e", "ihhx", spaceid, startpoint, numpoints, buf); /* Check args */ if (NULL == buf) @@ -2200,7 +2216,7 @@ done: } /* end H5S__point_project_scalar() */ /*------------------------------------------------------------------------- - * Function: H5S_point_project_simple + * Function: H5S__point_project_simple * * Purpose: Projects a point selection onto/into a simple dataspace * of a different rank @@ -2330,6 +2346,10 @@ H5S__point_project_simple(const H5S_t *base_space, H5S_t *new_space, hsize_t *of } /* end for */ } /* end else */ + /* Clear cached iteration point */ + new_space->select.sel_info.pnt_lst->last_idx = 0; + new_space->select.sel_info.pnt_lst->last_idx_pnt = NULL; + /* Number of elements selected will be the same */ new_space->select.num_elem = base_space->select.num_elem; diff --git a/src/H5Sprivate.h b/src/H5Sprivate.h index 76ed237..56c1646 100644 --- a/src/H5Sprivate.h +++ b/src/H5Sprivate.h @@ -201,6 +201,7 @@ struct H5O_loc_t; typedef struct H5S_t H5S_t; /* Operations on dataspaces */ +H5_DLL herr_t H5S_init(void); H5_DLL H5S_t * H5S_copy(const H5S_t *src, hbool_t share_selection, hbool_t copy_max); H5_DLL herr_t H5S_close(H5S_t *ds); H5_DLL H5S_class_t H5S_get_simple_extent_type(const H5S_t *ds); @@ -275,7 +276,7 @@ H5_DLL herr_t H5S_select_elements(H5S_t *space, H5S_seloper_t op, size_t num_ele /* Operations on hyperslab selections */ H5_DLL herr_t H5S_select_hyperslab(H5S_t *space, H5S_seloper_t op, const hsize_t start[], const hsize_t *stride, const hsize_t count[], const hsize_t *block); -H5_DLL herr_t H5S_combine_hyperslab(H5S_t *old_space, H5S_seloper_t op, const hsize_t start[], +H5_DLL herr_t H5S_combine_hyperslab(const H5S_t *old_space, H5S_seloper_t op, const hsize_t start[], const hsize_t *stride, const hsize_t count[], const hsize_t *block, H5S_t **new_space); H5_DLL herr_t H5S_hyper_add_span_element(H5S_t *space, unsigned rank, const hsize_t *coords); diff --git a/src/H5Spublic.h b/src/H5Spublic.h index 6befa55..fd85dcc 100644 --- a/src/H5Spublic.h +++ b/src/H5Spublic.h @@ -120,59 +120,1220 @@ typedef enum { extern "C" { #endif -/* Operations on dataspaces */ -H5_DLL hid_t H5Screate(H5S_class_t type); -H5_DLL hid_t H5Screate_simple(int rank, const hsize_t dims[], const hsize_t maxdims[]); -H5_DLL herr_t H5Sset_extent_simple(hid_t space_id, int rank, const hsize_t dims[], const hsize_t max[]); -H5_DLL hid_t H5Scopy(hid_t space_id); -H5_DLL herr_t H5Sclose(hid_t space_id); -H5_DLL herr_t H5Sencode2(hid_t obj_id, void *buf, size_t *nalloc, hid_t fapl); -H5_DLL hid_t H5Sdecode(const void *buf); -H5_DLL hssize_t H5Sget_simple_extent_npoints(hid_t space_id); -H5_DLL int H5Sget_simple_extent_ndims(hid_t space_id); -H5_DLL int H5Sget_simple_extent_dims(hid_t space_id, hsize_t dims[], hsize_t maxdims[]); -H5_DLL htri_t H5Sis_simple(hid_t space_id); -H5_DLL H5S_class_t H5Sget_simple_extent_type(hid_t space_id); -H5_DLL herr_t H5Sset_extent_none(hid_t space_id); -H5_DLL herr_t H5Sextent_copy(hid_t dst_id, hid_t src_id); -H5_DLL htri_t H5Sextent_equal(hid_t sid1, hid_t sid2); +/* Operations on dataspaces, dataspace selections and selection iterators */ -/* Operations on dataspace selections */ -H5_DLL H5S_sel_type H5Sget_select_type(hid_t spaceid); -H5_DLL hssize_t H5Sget_select_npoints(hid_t spaceid); -H5_DLL herr_t H5Sselect_copy(hid_t dst_id, hid_t src_id); -H5_DLL htri_t H5Sselect_valid(hid_t spaceid); -H5_DLL herr_t H5Sselect_adjust(hid_t spaceid, const hssize_t *offset); -H5_DLL herr_t H5Sget_select_bounds(hid_t spaceid, hsize_t start[], hsize_t end[]); -H5_DLL htri_t H5Sselect_shape_same(hid_t space1_id, hid_t space2_id); -H5_DLL htri_t H5Sselect_intersect_block(hid_t space_id, const hsize_t *start, const hsize_t *end); -H5_DLL herr_t H5Soffset_simple(hid_t space_id, const hssize_t *offset); -H5_DLL herr_t H5Sselect_all(hid_t spaceid); -H5_DLL herr_t H5Sselect_none(hid_t spaceid); -H5_DLL herr_t H5Sselect_elements(hid_t space_id, H5S_seloper_t op, size_t num_elem, const hsize_t *coord); +/** + * \ingroup H5S + * + * \brief Releases and terminates access to a dataspace + * + * \space_id + * + * \return \herr_t + * + * \details H5Sclose() releases a dataspace. Further access through the + * dataspace identifier is illegal. Failure to release a dataspace with this + * call will result in resource leaks. + * + * \version 1.4.0 Fortran subroutine introduced in this release. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sclose(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Performs an operation on a hyperslab and an existing selection and + * returns the resulting selection + * + * \space_id + * \param[in] op Operation to perform on the current selection + * \param[in] start Offset of the start of of the hyperslab + * \param[in] stride Hyperslab stride + * \param[in] count Number of blocks included in the hyperslab + * \param[in] block Size of a block in the hyperslab + * + * \return \hid_tv{dataspace} + * + * \details H5Scombine_hyperslab() combines a hyperslab selection specified + * by \p start, \p stride, \p count and \p block with the current + * selection for the dataspace \p space_id, creating a new dataspace + * to return the generated selection. If the current selection is + * not a hyperslab, it is freed and the hyperslab parameters passed + * in are combined with the #H5S_SEL_ALL hyperslab (ie. a selection + * composing the entire current extent). If either \p stride or + * \p block is NULL, then it will be set to \p 1. + * + * \since 1.12.0 + * + */ +H5_DLL hid_t H5Scombine_hyperslab(hid_t space_id, H5S_seloper_t op, const hsize_t start[], + const hsize_t stride[], const hsize_t count[], const hsize_t block[]); +/** + * \ingroup H5S + * + * \brief Combine two hyperslab selections with an operation, returning a + * dataspace with the resulting selection + * + * \space_id{space1_id} + * \param[in] op Selection operator + * \space_id{space2_id} + * + * \return \hid_t{dataspace} + * + * \details H5Scombine_select() combines two hyperslab selections + * \p space1_id and \p space2_id with an operation, returning a + * new dataspace with the resulting selection. The dataspace extent + * from \p space1_id is copied for the dataspace extent of the + * newly created dataspace. + * + * \since 1.12.0 + * + */ +H5_DLL hid_t H5Scombine_select(hid_t space1_id, H5S_seloper_t op, hid_t space2_id); +/** + * \ingroup H5S + * + * \brief Creates an exact copy of a dataspace + * + * \space_id + * + * \return \hid_tv{dataspace} + * + * \details H5Scopy() creates a new dataspace which is an exact copy of the + * dataspace identified by \p space_id. The dataspace identifier + * returned from this function should be released with H5Sclose() + * or resource leaks will occur. + * + * \version 1.4.0 Fortran subroutine introduced. + * \since 1.0.0 + * + */ +H5_DLL hid_t H5Scopy(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Creates a new dataspace of a specified type + * + * \param[in] type Type of dataspace to be created + * + * \return \hid_t{dataspace} + * + * \details H5Screate() creates a new dataspace of a particular type. Currently + * supported types are #H5S_SCALAR, #H5S_SIMPLE, and #H5S_NULL. + * + * Further dataspace types may be added later. + * + * A scalar dataspace, #H5S_SCALAR, has a single element, though that + * element may be of a complex datatype, such as a compound or array + * datatype. By convention, the rank of a scalar dataspace is always \p 0 + * (zero); think of it geometrically as a single, dimensionless point, + * though that point can be complex. + * + * A simple dataspace, #H5S_SIMPLE, consists of a regular array of elements. + * + * A null dataspace, #H5S_NULL, has no data elements. + * + * The dataspace identifier returned by this function can be released with + * H5Sclose() so that resource leaks will not occur. + * + * \version 1.4.0 Fortran subroutine introduced. + * \since 1.0.0 + * + */ +H5_DLL hid_t H5Screate(H5S_class_t type); +/** + * \ingroup H5S + * \brief Creates a new simple dataspace and opens it for access + * + * \param[in] rank Number of dimensions of dataspace + * \param[in] dims Array specifying the size of each dimension + * \param[in] maxdims Array specifying the maximum size of each dimension + * + * \return \hid_t{dataspace} + * + * \details H5Screate_simple() creates a new simple dataspace and opens it + * for access, returning a dataspace identifier. + * + * \p rank is the number of dimensions used in the dataspace. + * + * \p dims is a one-dimensional array of size rank specifying the + * size of each dimension of the dataset. \p maxdims is an array of + * the same size specifying the upper limit on the size of each + * dimension. + * + * Any element of \p dims can be \p 0 (zero). Note that no data can + * be written to a dataset if the size of any dimension of its current + * dataspace is \p 0. This is sometimes a useful initial state for + * a dataset. + * + * \p maxdims may be the null pointer, in which case the upper limit + * is the same as \p dims. Otherwise, no element of \p maxdims + * should be smaller than the corresponding element of \p dims. + * + * If an element of \p maxdims is #H5S_UNLIMITED, the maximum size of + * the corresponding dimension is unlimited. + * + * Any dataset with an unlimited dimension must also be chunked; see + * H5Pset_chunk(). Similarly, a dataset must be chunked if \p dims + * does not equal \p maxdims. + * + * The dataspace identifier returned from this function must be + * released with H5Sclose() or resource leaks will occur. + * + * \note Once a dataspace has been created, specific regions or elements in + * the dataspace can be selected and selections can be removed, as well. + * For example, H5Sselect_hyperslab() selects a region in a dataspace and + * H5Sselect_elements() selects array elements in a dataspace. These + * functions are used for subsetting. H5Sselect_none() removes all + * selections from a dataspace and is used in Parallel HDF5 when a process + * does not have or need to write data. + * + * \version 1.4.0 Fortran subroutine introduced. + * + * \since 1.0.0 + * + */ +H5_DLL hid_t H5Screate_simple(int rank, const hsize_t dims[], const hsize_t maxdims[]); +/** + * \ingroup H5S + * + * \brief Decodes a binary object description of data space and returns a + * new object handle + * + * \param[in] buf Buffer for the data space object to be decoded + * + * \return \hid_t{dataspace} + * + * \details Given an object description of a dataspace in binary in a + * buffer, H5Sdecode() reconstructs the HDF5 data type object and + * returns a new object handle for it. The binary description of the + * object is encoded by H5Sencode(). The user is responsible for + * passing in the right buffer. The types of dataspace addressed + * in this function are null, scalar, and simple space. For a + * simple dataspace, the selection information (for example, + * hyperslab selection) is also encoded and decoded. A complex + * dataspace has not been implemented in the library. + * + * \since 1.8.0 + * + */ +H5_DLL hid_t H5Sdecode(const void *buf); +/** + * \ingroup H5S + * + * \brief Encodes a data space object description into a binary buffer + * + * \space_id{obj_id} + * \param[in,out] buf Buffer for the object to be encoded into; + * If the provided buffer is NULL, only the size + * of buffer needed is returned through \p nalloc. + * \param[in,out] nalloc The size of the allocated buffer + * \fapl_id{fapl} + * + * \return \herr_t + * + * \details Given the data space identifier \p obj_id, H5Sencode2() converts + * a data space description into binary form in a buffer. Using this + * binary form in the buffer, a data space object can be + * reconstructed with H5Sdecode() to return a new object handle + * (#hid_t) for this data space. + * + * A preliminary H5Sencode2() call can be made to determine the + * size of the buffer needed. This value is returned in \p nalloc. + * That value can then be assigned to \p nalloc for a second + * H5Sencode2() call, which will retrieve the actual encoded object. + * + * If the library determines that \p nalloc is not big enough for the + * object, it simply returns the size of the buffer needed through + * \p nalloc without encoding the provided buffer. + * + * The file access property list \p fapl_id is used to control the + * encoding via the \a libver_bounds property (see + * H5Pset_libver_bounds()). If the \a libver_bounds property is missing, + * H5Sencode2() proceeds as if the \a libver_bounds property were set to + * (#H5F_LIBVER_EARLIEST, #H5F_LIBVER_LATEST). (Functionally, + * H5Sencode1() is identical to H5Sencode2() with \a libver_bounds set to + * (#H5F_LIBVER_EARLIEST, #H5F_LIBVER_LATEST).) + * + * The types of data space that are addressed in this function are + * null, scalar, and simple space. For a simple data space, the + * information on the selection, for example, hyperslab selection, + * is also encoded and decoded. A complex data space has not been + * implemented in the library. + * + * \note Motivation: This function was introduced in HDF5-1.12 as part of the + * H5Sencode() format change to enable 64-bit selection encodings and + * a dataspace selection that is tied to a file. See the \ref_news_112 + * as well as the \ref_sencode_fmt_change. + * + * \since 1.12.0 + * + */ +H5_DLL herr_t H5Sencode2(hid_t obj_id, void *buf, size_t *nalloc, hid_t fapl); +/** + * \ingroup H5S + * + * \brief Copies the extent of a dataspace + * + * \space_id{dst_id} + * \space_id{src_id} + * + * \return \herr_t + * + * \details H5Sextent_copy() copies the extent from \p src_id to \p dst_id. + * This action may change the type of the dataspace. + * + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sextent_copy(hid_t dst_id, hid_t src_id); +/** + * \ingroup H5S + * + * \brief Determines whether two dataspace extents are equal + * + * \space_id{space1_id} + * \space_id{space2_id} + * + * \return \htri_t + * + * \details H5Sextent_equal() determines whether the dataspace extents of + * two dataspaces, \p space1_id and \p space2_id, are equal. + * + * \since 1.8.0 + * + */ +H5_DLL htri_t H5Sextent_equal(hid_t space1_id, hid_t space2_id); +/** + * \ingroup H5S + * + * \brief Retrieves a regular hyperslab selection + * + * \space_id{spaceid} + * \param[out] start Offset of the start of the regular hyperslab + * \param[out] stride Stride of the regular hyperslab + * \param[out] count Number of blocks in the regular hyperslab + * \param[out] block Size of a block in the regular hyperslab + * + * \return \herr_t + * + * \details H5Sget_regular_hyperslab() takes the dataspace identifier, + * \p spaceid, and retrieves the values of \p start, \p stride, + * \p count, and \p block for the regular hyperslab selection. + * + * A regular hyperslab selection is a hyperslab selection + * described by setting the \p offset, \p stride, \p count, and + * \p block parameters to the H5Sselect_hyperslab() call. If + * several calls to H5Sselect_hyperslab() are needed, the + * hyperslab selection is irregular. + * + * See H5Sselect_hyperslab() for descriptions of \p offset, + * \p stride, \p count, and \p block. + * + * \note If a hyperslab selection is originally regular, then becomes + * irregular through selection operations, and then becomes regular + * again, the final regular selection may be equivalent but not + * identical to the original regular selection. + * + * \since 1.10.0 + * + */ +H5_DLL htri_t H5Sget_regular_hyperslab(hid_t spaceid, hsize_t start[], hsize_t stride[], hsize_t count[], + hsize_t block[]); +/** + * \ingroup H5S + * + * \brief Gets the bounding box containing the current selection + * + * \space_id{spaceid} + * \param[out] start Starting coordinates of the bounding box + * \param[out] end Ending coordinates of the bounding box, i.e., the + * coordinates of the diagonally opposite corner + * + * \return \herr_t + * + * \details H5Sget_select_bounds() retrieves the coordinates of the bounding + * box containing the current selection and places them into + * user-supplied buffers. + * + * The \p start and \p end buffers must be large enough to hold + * the dataspace rank number of coordinates. + * + * The bounding box exactly contains the selection. I.e., if a + * 2-dimensional element selection is currently defined as containing + * the points (4,5), (6,8), and (10,7), then the bounding box + * will be (4, 5), (10, 8). + * + * The bounding box calculation includes the current offset of the + * selection within the dataspace extent. + * + * Calling this function on a \a none selection will fail. + * + * \version 1.6.0 The \p start and \p end parameters have changed from type + * \p hsize_t * to \p hssize_t *. + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.2.0 + * + */ +H5_DLL herr_t H5Sget_select_bounds(hid_t spaceid, hsize_t start[], hsize_t end[]); +/** + * \ingroup H5S + * + * \brief Gets the number of element points in the current selection + * + * \space_id{spaceid} + * + * \return Returns the number of element points in the current dataspace + * selection if successful. Otherwise returns a negative value. + * + * \details H5Sget_select_elem_npoints() returns the number of element + * points in the current dataspace selection, so that the element + * points can be retrieved with H5Sget_select_elem_pointlist(). + * (This is similar to the way that H5Sget_select_hyper_nblocks() + * and H5Sget_select_hyper_blocklist() work with hyperslab + * selections.) + * + * Coincidentally, H5Sget_select_npoints() and + * H5Sget_select_elem_npoints() will always return the same value + * when an element selection is queried, but + * H5Sget_select_elem_npoints() does not work with other selection + * types. + * + * \since 1.2.0 + * + */ H5_DLL hssize_t H5Sget_select_elem_npoints(hid_t spaceid); -H5_DLL herr_t H5Sget_select_elem_pointlist(hid_t spaceid, hsize_t startpoint, hsize_t numpoints, - hsize_t buf[/*numpoints*/]); -H5_DLL herr_t H5Sselect_hyperslab(hid_t space_id, H5S_seloper_t op, const hsize_t start[], - const hsize_t _stride[], const hsize_t count[], const hsize_t _block[]); -H5_DLL hid_t H5Scombine_hyperslab(hid_t space_id, H5S_seloper_t op, const hsize_t start[], - const hsize_t _stride[], const hsize_t count[], const hsize_t _block[]); -H5_DLL herr_t H5Smodify_select(hid_t space1_id, H5S_seloper_t op, hid_t space2_id); -H5_DLL hid_t H5Scombine_select(hid_t space1_id, H5S_seloper_t op, hid_t space2_id); -H5_DLL htri_t H5Sis_regular_hyperslab(hid_t spaceid); -H5_DLL htri_t H5Sget_regular_hyperslab(hid_t spaceid, hsize_t start[], hsize_t stride[], hsize_t count[], - hsize_t block[]); +/** + * \ingroup H5S + * + * \brief Gets the list of element points currently selected + * + * \space_id{spaceid} + * \param[in] startpoint Element point to start with + * \param[in] numpoints Number of element points to get + * \param[out] buf List of element points selected + * + * \details H5Sget_select_elem_pointlist() returns the list of element + * points in the current dataspace selection \p space_id. Starting + * with the \p startpoint in the list of points, \p numpoints + * points are put into the user's buffer. If the user's buffer + * fills up before \p numpoints points are inserted, the buffer + * will contain only as many points as fit. + * + * The element point coordinates have the same dimensionality + * (rank) as the dataspace they are located within. The list of + * element points is formatted as follows:\n + * \<coordinate\>, followed by\n + * the next coordinate,\n + * etc.\n + * until all of the selected element points have been listed. + * + * The points are returned in the order they will be iterated + * through when the selection is read/written from/to disk. + * + * \since 1.2.0 + * + */ +H5_DLL herr_t H5Sget_select_elem_pointlist(hid_t spaceid, hsize_t startpoint, hsize_t numpoints, + hsize_t buf[/*numpoints*/]); +/** + * \ingroup H5S + * + * \brief Gets the list of hyperslab blocks currently selected + * + * \space_id{spaceid} + * \param[in] startblock Hyperslab block to start with + * \param[in] numblocks Number of hyperslab blocks to get + * \param[out] buf List of hyperslab blocks selected + * + * \return \herr_t + * + * \details H5Sget_select_hyper_blocklist() returns a list of the hyperslab + * blocks currently selected. Starting with the \p startblock-th block + * in the list of blocks, \p numblocks blocks are put into the + * user's buffer. If the user's buffer fills up before \p numblocks + * blocks are inserted, the buffer will contain only as many blocks + * as fit. + * + * The block coordinates have the same dimensionality (rank) as the + * dataspace they are located within. The list of blocks is + * formatted as follows:\n + * \<"start" coordinate\>, immediately followed by\n + * \<"opposite" corner coordinate\>, followed by\n + * the next "start" and "opposite" coordinates,\n + * etc. until all of the selected blocks have been listed.\n + * No guarantee of any order of the blocks is implied. + * + * \since 1.2.0 + * + */ +H5_DLL herr_t H5Sget_select_hyper_blocklist(hid_t spaceid, hsize_t startblock, hsize_t numblocks, + hsize_t buf[/*numblocks*/]); +/** + * \ingroup H5S + * + * \brief Get number of hyperslab blocks + * + * \space_id{spaceid} + * + * \return Returns the number of hyperslab blocks in the current dataspace + * selection if successful. Otherwise returns a negative value. + * + * \details H5Sget_select_hyper_nblocks() returns the number of hyperslab + * blocks in the current dataspace selection. + * + * \since 1.2.0 + * + */ H5_DLL hssize_t H5Sget_select_hyper_nblocks(hid_t spaceid); -H5_DLL herr_t H5Sget_select_hyper_blocklist(hid_t spaceid, hsize_t startblock, hsize_t numblocks, - hsize_t buf[/*numblocks*/]); -H5_DLL hid_t H5Sselect_project_intersection(hid_t src_space_id, hid_t dst_space_id, - hid_t src_intersect_space_id); - -/* Operations on dataspace selection iterators */ -H5_DLL hid_t H5Ssel_iter_create(hid_t spaceid, size_t elmt_size, unsigned flags); +/** + * \ingroup H5S + * + * \brief Determines the number of elements in a dataspace selection + * + * \space_id{spaceid} + * + * \return Returns the number of elements in the selection if successful; + * otherwise returns a negative value. + * + * \details H5Sget_select_npoints() determines the number of elements in + * the current selection of a dataspace. It works with any + * selection type, and is the correct way to retrieve the number + * of elements in a selection. + * + * \version 1.4.0 Fortran subroutine introduced in this release. + * \since 1.0.0 + * + */ +H5_DLL hssize_t H5Sget_select_npoints(hid_t spaceid); +/** + * \ingroup H5S + * + * \brief Determines the type of the dataspace selection + * + * \space_id{spaceid} + * + * \return Returns the dataspace selection type, a value of the enumerated + * datatype #H5S_sel_type, if successful. + * + * \details H5Sget_select_type() retrieves the type of dataspace selection + * currently defined for the dataspace \p space_id. Valid values + * for the dataspace selection type are: + * + * <table> + * <tr> + * <td>#H5S_SEL_NONE</td> + * <td>No selection is defined</td> + * </tr> + * <tr> + * <td>#H5S_SEL_POINTS</td> + * <td>A sequence of points is selected</td> + * </tr> + * <tr> + * <td>#H5S_SEL_HYPERSLABS</td> + * <td>A hyperslab or compound hyperslab is selected</td> + * </tr> + * <tr> + * <td>#H5S_SEL_ALL</td> + * <td>The entire dataset is selected</td> + * </tr> + * </table> + * + * Otherwise returns a negative value. + * + * \since 1.6.0 + * + */ +H5_DLL H5S_sel_type H5Sget_select_type(hid_t spaceid); +/** + * \ingroup H5S + * + * \brief Retrieves dataspace dimension size and maximum size + * + * \space_id + * \param[out] dims Pointer to array to store the size of each dimension + * \param[out] maxdims Pointer to array to store the maximum size of each + * dimension + * + * \return Returns the number of dimensions in the dataspace if successful; + * otherwise returns a negative value. + * + * \details H5Sget_simple_extent_dims() returns the size and maximum sizes + * of each dimension of a dataspace \p space_id through the \p dims + * and \p maxdims parameters. + * + * Either or both of \p dims and \p maxdims may be NULL. + * + * If a value in the returned array \p maxdims is #H5S_UNLIMITED (-1), + * the maximum size of that dimension is unlimited. + * + * \version 1.4.0 Fortran subroutine introduced. + * \since 1.0.0 + * + */ +H5_DLL int H5Sget_simple_extent_dims(hid_t space_id, hsize_t dims[], hsize_t maxdims[]); +/** + * \ingroup H5S + * + * \brief Determines the dimensionality of a dataspace + * + * \space_id + * + * \return Returns the number of dimensions in the dataspace if successful; + * otherwise returns a negative value. + * + * \details H5Sget_simple_extent_ndims() determines the dimensionality (or + * rank) of a dataspace. + * + * \version 1.4.0 Fortran subroutine introduced. + * \since 1.0.0 + * + */ +H5_DLL int H5Sget_simple_extent_ndims(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Determines the number of elements in a dataspace + * + * \space_id + * + * \return Returns the number of elements in the dataspace if successful; + * otherwise returns a negative value. + * + * \details H5Sget_simple_extent_npoints() determines the number of elements + * in a dataspace \p space_id. For example, a simple 3-dimensional + * dataspace with dimensions 2, 3, and 4 would have 24 elements. + * + * \version 1.4.0 Fortran subroutine introduced. + * \since 1.0.0 + * + */ +H5_DLL hssize_t H5Sget_simple_extent_npoints(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Determines the current class of a dataspace + * + * \space_id + * + * \return Returns a dataspace class name if successful; + * otherwise #H5S_NO_CLASS (-1). + * + * \details H5Sget_simple_extent_type() determines the current class of a + * dataspace \p space_id. + * + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL H5S_class_t H5Sget_simple_extent_type(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Determines if a hyperslab selection is regular + * + * \space_id{spaceid} + * + * \return \htri_t + * + * \details H5Sis_regular_hyperslab() takes the dataspace identifier, + * \p spaceid, and queries the type of the hyperslab selection. + * + * A regular hyperslab selection is a hyperslab selection described + * by setting the offset, stride, count, and block parameters for + * a single H5Sselect_hyperslab() call. If several calls to + * H5Sselect_hyperslab() are needed, then the hyperslab selection + * is irregular. + * + * \since 1.10.0 + * + */ +H5_DLL htri_t H5Sis_regular_hyperslab(hid_t spaceid); +/** + * \ingroup H5S + * + * \brief Determines whether a dataspace is a simple dataspace + * + * \space_id + * + * \return \htri_t + * + * \details H5Sis_simple() determines whether or not a dataspace is a simple + * dataspace. + * + * \note Currently, all dataspace objects are simple dataspaces; complex + * dataspace support will be added in the future. + * + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL htri_t H5Sis_simple(hid_t space_id); +/** + * \ingroup H5S + * + * \brief Refines a hyperslab selection with an operation, using a second + * hyperslab to modify it + * + * \space_id{space1_id} + * \param[in] op Selection operator + * \space_id{space2_id} + * + * \return \herr_t + * + * \details H5Smodify_select() refines an existing hyperslab selection + * \p space1_id with an operation \p op, using a second hyperslab + * \p space2_id. The first selection is modified to contain the + * result of \p space1_id operated on by \p space2_id. + * + * \since 1.12.0 + * + */ +H5_DLL herr_t H5Smodify_select(hid_t space1_id, H5S_seloper_t op, hid_t space2_id); +/** + * \ingroup H5S + * + * \brief Sets the offset of a simple dataspace + * + * \space_id + * \param[in] offset The offset at which to position the selection + * + * \return \herr_t + * + * \details H5Soffset_simple() sets the offset of a simple dataspace + * \p space_id. The offset array must be the same number of + * elements as the number of dimensions for the dataspace. If the + * \p offset array is set to NULL, the offset for the dataspace is + * reset to 0. + * + * This function allows the same shaped selection to be moved to + * different locations within a dataspace without requiring it to + * be redefined. + * + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Soffset_simple(hid_t space_id, const hssize_t *offset); +/** + * \ingroup H5S + * + * \brief Closes a dataspace selection iterator + * + * \space_id{sel_iter_id} + * + * \return \herr_t + * + * \details H5Ssel_iter_close() closes a dataspace selection iterator + * specified by \p sel_iter_id, releasing its state. + * + * \since 1.12.0 + * + */ +H5_DLL herr_t H5Ssel_iter_close(hid_t sel_iter_id); +/**\ingroup H5S + * + * \brief Creates a dataspace selection iterator for a dataspace's selection + * + * \space_id{spaceid} + * \param[in] elmt_size Size of element in the selection + * \param[in] flags Selection iterator flag + * + * \return \hid_t{valid dataspace selection iterator} + * + * \details H5Ssel_iter_create() creates a selection iterator and initializes + * it to start at the first element selected in the dataspace. + * + * \since 1.12.0 + * + */ +H5_DLL hid_t H5Ssel_iter_create(hid_t spaceid, size_t elmt_size, unsigned flags); +/** + * \ingroup H5S + * + * \brief Retrieves a list of offset / length sequences for the elements in + * an iterator + * + * \space_id{sel_iter_id} + * \param[in] maxseq Maximum number of sequences to retrieve + * \param[in] maxbytes Maximum number of bytes to retrieve in sequences + * \param[out] nseq Number of sequences retrieved + * \param[out] nbytes Number of bytes retrieved, in all sequences + * \param[out] off Array of sequence offsets + * \param[out] len Array of sequence lengths + * + * \return \herr_t + * + * \details H5Ssel_iter_get_seq_list() retrieves a list of offset / length + * pairs (a list of "sequences") matching the selected elements for + * an iterator \p sel_iter_id, according to the iteration order for + * the iterator. The lengths returned are in bytes, not elements. + * + * Note that the iteration order for "all" and "hyperslab" + * selections is row-major (i.e. "C-ordered"), but the iteration + * order for "point" selections is "in order selected", unless the + * #H5S_SEL_ITER_GET_SEQ_LIST_SORTED flag is passed to + * H5Ssel_iter_create() for a point selection. + * + * \p maxseq and \p maxbytes specify the most sequences or bytes + * possible to place into the \p off and \p len arrays. \p nseq and + * \p nbytes return the actual number of sequences and bytes put + * into the arrays. + * + * Each call to H5Ssel_iter_get_seq_list() will retrieve the next + * set of sequences for the selection being iterated over. + * + * The total number of bytes possible to retrieve from a selection + * iterator is the \p elmt_size passed to H5Ssel_iter_create() + * multiplied by the number of elements selected in the dataspace + * the iterator was created from (which can be retrieved with + * H5Sget_select_npoints(). When there are no further sequences of + * elements to retrieve, calls to this routine will set \p nseq + * and \p nbytes to zero. + * + * \since 1.12.0 + * + */ H5_DLL herr_t H5Ssel_iter_get_seq_list(hid_t sel_iter_id, size_t maxseq, size_t maxbytes, size_t *nseq, size_t *nbytes, hsize_t *off, size_t *len); -H5_DLL herr_t H5Ssel_iter_close(hid_t sel_iter_id); +/** + * \ingroup H5S + * + * \brief Resets a dataspace selection iterator back to an initial state + * + * \param[in] sel_iter_id Identifier of the dataspace selection iterator + * to reset + * \param[in] space_id Identifier of the dataspace with selection to + * iterate over + * + * \return \herr_t + * + * \details H5Ssel_iter_reset() resets a dataspace selection iterator back to + * an initial state so that the iterator may be used for iteration + * once again. + * + * \since 1.12.1 + * + */ +H5_DLL herr_t H5Ssel_iter_reset(hid_t sel_iter_id, hid_t space_id); +/** + * \ingroup H5S + * + * \brief Adjusts a selection by subtracting an offset + * + * \space_id{spaceid} + * \param[in] offset Offset to subtract + * + * \return \herr_t + * + * \details H5Sselect_adjust() shifts a dataspace selection by a specified + * logical offset within the dataspace extent. + * + * \note This can be useful for VOL developers to implement chunked datasets. + * + * \since 1.12.0 + */ +H5_DLL herr_t H5Sselect_adjust(hid_t spaceid, const hssize_t *offset); +/** + * \ingroup H5S + * + * \brief Selects an entire dataspace + * + * \space_id{spaceid} + * + * \return \herr_t + * + * \details H5Sselect_all() selects the entire extent of the dataspace + * \p dspace_id. + * + * More specifically, H5Sselect_all() sets the selection type to + * #H5S_SEL_ALL, which specifies the entire dataspace anywhere it + * is applied. + * + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sselect_all(hid_t spaceid); +/** + * \ingroup H5S + * + * \brief Copies a selection from one dataspace to another + * + * \space_id{dst_id} + * \space_id{src_id} + * + * \return \herr_t + * + * \details H5Sselect_copy() copies all selection information (including + * offset) from the source dataspace \p src_id to the destination + * dataspace \p dst_id. + * + * \since 1.12.0 + * + */ +H5_DLL herr_t H5Sselect_copy(hid_t dst_id, hid_t src_id); +/** + * \ingroup H5S + * + * \brief Selects array elements to be included in the selection for a + * dataspace + * + * \space_id + * \param[in] op Operator specifying how the new selection is to be + * combined with the existing selection for the dataspace + * \param[in] num_elem Number of elements to be selected + * \param[in] coord A pointer to a buffer containing a serialized copy of + * a 2-dimensional array of zero-based values specifying + * the coordinates of the elements in the point selection + * + * \return \herr_t + * + * \details H5Sselect_elements() selects array elements to be included in + * the selection for the \p space_id dataspace. This is referred + * to as a point selection. + * + * The number of elements selected is set in the \p num_elements + * parameter. + * + * The \p coord parameter is a pointer to a buffer containing a + * serialized 2-dimensional array of size \p num_elements by the + * rank of the dataspace. The array lists dataset elements in the + * point selection; that is, it’s a list of of zero-based values + * specifying the coordinates in the dataset of the selected + * elements. The order of the element coordinates in the \p coord + * array specifies the order in which the array elements are + * iterated through when I/O is performed. Duplicate coordinate + * locations are not checked for. See below for examples of the + * mapping between the serialized contents of the buffer and the + * point selection array that it represents. + * + * The selection operator \p op determines how the new selection + * is to be combined with the previously existing selection for + * the dataspace. The following operators are supported: + * + * <table> + * <tr> + * <td>#H5S_SELECT_SET</td> + * <td>Replaces the existing selection with the parameters from + * this call. Overlapping blocks are not supported with this + * operator. Adds the new selection to the existing selection. + * </td> + * </tr> + * <tr> + * <td>#H5S_SELECT_APPEND</td> + * <td>Adds the new selection following the last element of the + * existing selection.</td> + * </tr> + * <tr> + * <td>#H5S_SELECT_PREPEND</td> + * <td>Adds the new selection preceding the first element of the + * existing selection.</td> + * </tr> + * </table> + * + * <b>Mapping the serialized \p coord buffer to a 2-dimensional + * point selection array:</b> + * To illustrate the construction of the contents of the \p coord + * buffer, consider two simple examples: a selection of 5 points in + * a 1-dimensional array and a selection of 3 points in a + * 4-dimensional array. + * + * In the 1D case, we will be selecting five points and a 1D + * dataspace has rank 1, so the selection will be described in a + * 5-by-1 array. To select the 1st, 14th, 17th, 23rd, 8th elements + * of the dataset, the selection array would be as follows + * (remembering that point coordinates are zero-based): + * \n 0 + * \n 13 + * \n 16 + * \n 22 + * \n 7 + * + * This point selection array will be serialized in the \p coord + * buffer as: + * \n 0 13 16 22 7 + * + * In the 4D case, we will be selecting three points and a 4D + * dataspace has rank 4, so the selection will be described in a + * 3-by-4 array. To select the points (1,1,1,1), (14,6,12,18), and + * (8,22,30,22), the point selection array would be as follows: + * \n 0 0 0 0 + * \n 13 5 11 17 + * \n 7 21 29 21 + * + * This point selection array will be serialized in the \p coord + * buffer as: + * \n 0 0 0 0 13 5 11 17 7 21 29 21 + * + * \version 1.6.4 C coord parameter type changed to \p const hsize_t. + * \version 1.6.4 Fortran \p coord parameter type changed to \p INTEGER(HSIZE_T). + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sselect_elements(hid_t space_id, H5S_seloper_t op, size_t num_elem, const hsize_t *coord); +/** + * \ingroup H5S + * + * \brief Selects a hyperslab region to add to the current selected region + * + * \space_id + * \param[in] op Operation to perform on current selection + * \param[in] start Offset of start of hyperslab + * \param[in] stride Hyperslab stride + * \param[in] count Number of blocks included in hyperslab + * \param[in] block Size of block in hyperslab + * + * \return \herr_t + * + * \details H5Sselect_hyperslab() selects a hyperslab region to add to the + * current selected region for the dataspace specified by + * \p space_id. + * + * The \p start, \p stride, \p count, and \p block arrays must be the + * same size as the rank of the dataspace. For example, if the + * dataspace is 4-dimensional, each of these parameters must be a + * 1-dimensional array of size 4. + * + * The selection operator \p op determines how the new selection + * is to be combined with the already existing selection for the + * dataspace. The following operators are supported: + * + * <table> + * <tr> + * <td>#H5S_SELECT_SET</td> + * <td>Replaces the existing selection with the + * parameters from this call. Overlapping blocks + * are not supported with this operator.</td> + * </tr> + * <tr> + * <td>#H5S_SELECT_OR</td> + * <td>Adds the new selection to the existing selection. + * (Binary OR)</td> + * </tr> + * <tr> + * <td>#H5S_SELECT_AND</td> + * <td>Retains only the overlapping portions of the + * new selection and the existing selection. + * (Binary AND)</td> + * </tr> + * <tr> + * <td>#H5S_SELECT_XOR</td> + * <td>Retains only the elements that are members of + * the new selection or the existing selection, + * excluding elements that are members of both + * selections. (Binary exclusive-OR, XOR) + * </td> + * </tr> + * <tr> + * <td>#H5S_SELECT_NOTB</td> + * <td>Retains only elements of the existing selection + * that are not in the new selection.</td> + * </tr> + * <tr> + * <td>#H5S_SELECT_NOTA</td> + * <td>Retains only elements of the new selection that + * are not in the existing selection.</td> + * </tr> + * </table> + * + * The \p start array specifies the offset of the starting element + * of the specified hyperslab. + * + * The \p stride array chooses array locations from the dataspace with + * each value in the \p stride array determining how many elements to + * move in each dimension. Setting a value in the \p stride array to + * \p 1 moves to each element in that dimension of the dataspace; + * setting a value of \p 2 in allocation in the \p stride array moves + * to every other element in that dimension of the dataspace. In + * other words, the \p stride determines the number of elements to + * move from the \p start location in each dimension. Stride values + * of \p 0 are not allowed. If the \p stride parameter is NULL, a + * contiguous hyperslab is selected (as if each value in the \p stride + * array were set to \p 1). + * + * The \p count array determines how many blocks to select from the + * dataspace, in each dimension. + * + * The \p block array determines the size of the element block + * selected from the dataspace. If the \p block parameter is set to + * NULL, the block size defaults to a single element in each dimension + * (as if each value in the \p block array were set to \p 1). + * + * For example, consider a 2-dimensional dataspace with hyperslab + * selection settings as follows: the \p start offset is specified as + * [1,1], \p stride is [4,4], \p count is [3,7], and \p block is [2,2]. + * In C, these settings will specify a hyperslab consisting of 21 + * 2x2 blocks of array elements starting with location (1,1) with the + * selected blocks at locations (1,1), (5,1), (9,1), (1,5), (5,5), etc.; + * in Fortran, they will specify a hyperslab consisting of 21 2x2 + * blocks of array elements starting with location (2,2) with the + * selected blocks at locations (2,2), (6,2), (10,2), (2,6), (6,6), etc. + * + * Regions selected with this function call default to C order + * iteration when I/O is performed. + * + * \version 1.4.0 Fortran subroutine introduced in this release. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sselect_hyperslab(hid_t space_id, H5S_seloper_t op, const hsize_t start[], + const hsize_t stride[], const hsize_t count[], const hsize_t block[]); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Checks if current selection intersects with a block + * + * \space_id + * \param[in] start Starting coordinate of block + * \param[in] end Opposite ("ending") coordinate of block + * + * \return \htri_t + * + * \details H5Sselect_intersect_block() checks to see if the current + * selection \p space_id in the dataspace intersects with the block + * specified by \p start and \p end. + * + * \note Assumes that \p start & \p end block bounds are inclusive, so + * \p start == \p end value is OK. + * + * \since 1.12.0 + * + */ +H5_DLL htri_t H5Sselect_intersect_block(hid_t space_id, const hsize_t *start, const hsize_t *end); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Resets the selection region to include no elements + * + * \space_id{spaceid} + * + * \return \herr_t + * + * \details H5Sselect_none() resets the selection region for the dataspace + * \p space_id to include no elements. + * + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sselect_none(hid_t spaceid); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Projects the intersection of two source selections to a + * destination selection + * + * \space_id{src_space_id} + * \space_id{dst_space_id} + * \space_id{src_intersect_space_id} + * + * \return Returns a dataspace with a selection equal to the intersection of + * \p src_intersect_space_id and \p src_space_id projected from + * \p src_space to \p dst_space on success, negative on failure. + * + * \details H5Sselect_project_intersection() computes the intersection + * between two dataspace selections and projects that intersection + * into a third selection.This can be useful for VOL developers to + * implement chunked or virtual datasets. + * + * \since 1.12.0 + * + */ +H5_DLL hid_t H5Sselect_project_intersection(hid_t src_space_id, hid_t dst_space_id, + hid_t src_intersect_space_id); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Checks if two selections are the same shape + * + * \space_id{space1_id} + * \space_id{space2_id} + * + * \return \htri_t + * + * \details H5Sselect_shape_same() checks to see if the current selection + * in the dataspaces are the same dimensionality and shape. + * + * This is primarily used for reading the entire selection in + * one swoop. + * + * \since 1.12.0 + * + */ +H5_DLL htri_t H5Sselect_shape_same(hid_t space1_id, hid_t space2_id); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Verifies that the selection is within the extent of the dataspace + * + * \space_id{spaceid} + * + * \return \htri_t + * + * \details H5Sselect_valid() verifies that the selection for the dataspace + * \p space_id is within the extent of the dataspace if the current + * offset for the dataspace is used. + * + * \version 1.4.0 Fortran subroutine introduced in this release. + * \since 1.0.0 + * + */ +H5_DLL htri_t H5Sselect_valid(hid_t spaceid); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Resets the extent of a dataspace back to "none" + * + * \space_id + * + * \return \herr_t + * + * \details H5Sset_extent_none() resets the type of a dataspace to + * #H5S_NULL with no extent information stored for the dataspace. + * + * \version 1.10.7, 1.12.1 The function behavior changed. The previous + * behavior was to set the class to #H5S_NO_CLASS. + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sset_extent_none(hid_t space_id); +/*--------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Sets or resets the size of an existing dataspace + * + * \space_id + * \param[in] rank Rank, or dimensionality, of the dataspace + * \param[in] dims Array containing current size of dataspace + * \param[in] max Array containing maximum size of dataspace + * + * \return \herr_t + * + * \details H5Sset_extent_simple() sets or resets the size of an existing + * dataspace. + * + * \p rank is the dimensionality, or number of dimensions, of the + * dataspace. + * + * \p dims is an array of size \p rank which contains the new size + * of each dimension in the dataspace. \p max is an array of size + * \p rank which contains the maximum size of each dimension in + * the dataspace. + * + * Any previous extent is removed from the dataspace, the dataspace + * type is set to #H5S_SIMPLE, and the extent is set as specified. + * + * Note that a dataset must be chunked if \p dims does not equal + * \p max. + * + * + * \version 1.4.0 Fortran subroutine was introduced. + * \since 1.0.0 + * + */ +H5_DLL herr_t H5Sset_extent_simple(hid_t space_id, int rank, const hsize_t dims[], const hsize_t max[]); /* Symbols defined for compatibility with previous versions of the HDF5 API. * @@ -180,6 +1341,47 @@ H5_DLL herr_t H5Ssel_iter_close(hid_t sel_iter_id); */ #ifndef H5_NO_DEPRECATED_SYMBOLS /* Function prototypes */ +/* --------------------------------------------------------------------------*/ +/**\ingroup H5S + * + * \brief Encodes a data space object description into a binary buffer + * + * \space_id{obj_id} + * \param[in,out] buf Buffer for the object to be encoded into; + * If the provided buffer is NULL, only the size of + * buffer needed is returned through \p nalloc. + * \param[in,out] nalloc The size of the allocated buffer + * + * \return \herr_t + * + * \deprecated Deprecated in favor of H5Sencode2() + * + * \details Given the data space identifier \p obj_id, H5Sencode1() converts + * a data space description into binary form in a buffer. Using + * this binary form in the buffer, a data space object can be + * reconstructed using H5Sdecode() to return a new object handle + * (\p hid_t) for this data space. + * + * A preliminary H5Sencode1() call can be made to find out the size + * of the buffer needed. This value is returned as \p nalloc. That + * value can then be assigned to \p nalloc for a second H5Sencode1() + * call, which will retrieve the actual encoded object. + * + * If the library finds out \p nalloc is not big enough for the + * object, it simply returns the size of the buffer needed through + * \p nalloc without encoding the provided buffer. + * + * The types of data space addressed in this function are null, + * scalar, and simple space. For a simple data space, the information + * on the selection, for example, hyperslab selection, is also + * encoded and decoded. A complex data space has not been + * implemented in the library. + * + * \version 1.12.0 The function H5Sencode() was renamed H5Sencode1() and + * deprecated. + * \since 1.8.0 + * + */ H5_DLL herr_t H5Sencode1(hid_t obj_id, void *buf, size_t *nalloc); #endif /* H5_NO_DEPRECATED_SYMBOLS */ diff --git a/src/H5Sselect.c b/src/H5Sselect.c index d6244b8..7a0ea3c 100644 --- a/src/H5Sselect.c +++ b/src/H5Sselect.c @@ -51,9 +51,9 @@ /********************/ #ifdef LATER -static herr_t H5S_select_iter_block(const H5S_sel_iter_t *iter, hsize_t *start, hsize_t *end); -static htri_t H5S_select_iter_has_next_block(const H5S_sel_iter_t *iter); -static herr_t H5S_select_iter_next_block(H5S_sel_iter_t *iter); +static herr_t H5S__select_iter_block(const H5S_sel_iter_t *iter, hsize_t *start, hsize_t *end); +static htri_t H5S__select_iter_has_next_block(const H5S_sel_iter_t *iter); +static herr_t H5S__select_iter_next_block(H5S_sel_iter_t *iter); #endif /* LATER */ /*****************************/ @@ -1196,11 +1196,11 @@ H5S_select_iter_coords(const H5S_sel_iter_t *sel_iter, hsize_t *coords) /*-------------------------------------------------------------------------- NAME - H5S_select_iter_block + H5S__select_iter_block PURPOSE Get the block of the current iterator position USAGE - herr_t H5S_select_iter_block(sel_iter,start,end) + herr_t H5S__select_iter_block(sel_iter,start,end) const H5S_sel_iter_t *sel_iter; IN: Selection iterator to query hsize_t *start; OUT: Array to place iterator start block coordinates hsize_t *end; OUT: Array to place iterator end block coordinates @@ -1218,11 +1218,11 @@ H5S_select_iter_coords(const H5S_sel_iter_t *sel_iter, hsize_t *coords) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_select_iter_block(const H5S_sel_iter_t *iter, hsize_t *start, hsize_t *end) +H5S__select_iter_block(const H5S_sel_iter_t *iter, hsize_t *start, hsize_t *end) { herr_t ret_value; /* return value */ - FUNC_ENTER_NOAPI_NOINIT_NOERR + FUNC_ENTER_STATIC_NOERR /* Check args */ HDassert(iter); @@ -1233,7 +1233,7 @@ H5S_select_iter_block(const H5S_sel_iter_t *iter, hsize_t *start, hsize_t *end) ret_value = (*iter->type->iter_block)(iter, start, end); FUNC_LEAVE_NOAPI(ret_value) -} /* end H5S_select_iter_block() */ +} /* end H5S__select_iter_block() */ #endif /* LATER */ /*-------------------------------------------------------------------------- @@ -1276,11 +1276,11 @@ H5S_select_iter_nelmts(const H5S_sel_iter_t *sel_iter) /*-------------------------------------------------------------------------- NAME - H5S_select_iter_has_next_block + H5S__select_iter_has_next_block PURPOSE Check if there is another block available in the selection iterator USAGE - htri_t H5S_select_iter_has_next_block(sel_iter) + htri_t H5S__select_iter_has_next_block(sel_iter) const H5S_sel_iter_t *sel_iter; IN: Selection iterator to query RETURNS Non-negative on success, negative on failure. @@ -1296,11 +1296,11 @@ H5S_select_iter_nelmts(const H5S_sel_iter_t *sel_iter) REVISION LOG --------------------------------------------------------------------------*/ static htri_t -H5S_select_iter_has_next_block(const H5S_sel_iter_t *iter) +H5S__select_iter_has_next_block(const H5S_sel_iter_t *iter) { herr_t ret_value; /* return value */ - FUNC_ENTER_NOAPI_NOINIT_NOERR + FUNC_ENTER_STATIC_NOERR /* Check args */ HDassert(iter); @@ -1309,7 +1309,7 @@ H5S_select_iter_has_next_block(const H5S_sel_iter_t *iter) ret_value = (*iter->type->iter_has_next_block)(iter); FUNC_LEAVE_NOAPI(ret_value) -} /* end H5S_select_iter_has_next_block() */ +} /* end H5S__select_iter_has_next_block() */ #endif /* LATER */ /*-------------------------------------------------------------------------- @@ -1358,11 +1358,11 @@ H5S_select_iter_next(H5S_sel_iter_t *iter, size_t nelem) /*-------------------------------------------------------------------------- NAME - H5S_select_iter_next_block + H5S__select_iter_next_block PURPOSE Advance selection iterator to next block USAGE - herr_t H5S_select_iter_next_block(iter) + herr_t H5S__select_iter_next_block(iter) H5S_sel_iter_t *iter; IN/OUT: Selection iterator to change RETURNS Non-negative on success, negative on failure. @@ -1380,11 +1380,11 @@ H5S_select_iter_next(H5S_sel_iter_t *iter, size_t nelem) REVISION LOG --------------------------------------------------------------------------*/ static herr_t -H5S_select_iter_next_block(H5S_sel_iter_t *iter) +H5S__select_iter_next_block(H5S_sel_iter_t *iter) { herr_t ret_value; /* return value */ - FUNC_ENTER_NOAPI_NOINIT_NOERR + FUNC_ENTER_STATIC_NOERR /* Check args */ HDassert(iter); @@ -1393,7 +1393,7 @@ H5S_select_iter_next_block(H5S_sel_iter_t *iter) ret_value = (*iter->type->iter_next_block)(iter); FUNC_LEAVE_NOAPI(ret_value) -} /* end H5S_select_iter_next_block() */ +} /* end H5S__select_iter_next_block() */ #endif /* LATER */ /*------------------------------------------------------------------------- @@ -3089,6 +3089,87 @@ done: FUNC_LEAVE_API(ret_value) } /* end H5Ssel_iter_get_seq_list() */ +/*-------------------------------------------------------------------------- + NAME + H5Ssel_iter_reset + PURPOSE + Resets a dataspace selection iterator back to an initial state. + USAGE + herr_t H5Ssel_iter_reset(sel_iter_id) + hid_t sel_iter_id; IN: ID of the dataspace selection iterator to + reset + hid_t space_id; IN: ID of the dataspace with selection to + iterate over + RETURNS + Non-negative on success / Negative on failure + DESCRIPTION + Resets a dataspace selection iterator back to an initial state so that + the iterator may be used for iteration once again. + GLOBAL VARIABLES + COMMENTS, BUGS, ASSUMPTIONS + EXAMPLES + REVISION LOG +--------------------------------------------------------------------------*/ +herr_t +H5Ssel_iter_reset(hid_t sel_iter_id, hid_t space_id) +{ + H5S_sel_iter_t *sel_iter; + H5S_t * space; + herr_t ret_value = SUCCEED; + + FUNC_ENTER_API(FAIL) + H5TRACE2("e", "ii", sel_iter_id, space_id); + + /* Check args */ + if (NULL == (sel_iter = (H5S_sel_iter_t *)H5I_object_verify(sel_iter_id, H5I_SPACE_SEL_ITER))) + HGOTO_ERROR(H5E_DATASPACE, H5E_BADTYPE, FAIL, "not a dataspace selection iterator") + if (NULL == (space = (H5S_t *)H5I_object_verify(space_id, H5I_DATASPACE))) + HGOTO_ERROR(H5E_DATASPACE, H5E_BADTYPE, FAIL, "not a dataspace") + + /* Call selection type-specific release routine */ + if (H5S_SELECT_ITER_RELEASE(sel_iter) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, + "problem releasing a selection iterator's type-specific info") + + /* Simply re-initialize iterator */ + if (H5S_select_iter_init(sel_iter, space, sel_iter->elmt_size, sel_iter->flags) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to re-initialize selection iterator") + +done: + FUNC_LEAVE_API(ret_value) +} /* end H5Ssel_iter_reset() */ + +/*------------------------------------------------------------------------- + * Function: H5S__sel_iter_close_cb + * + * Purpose: Called when the ref count reaches zero on a selection iterator's ID + * + * Return: Non-negative on success / Negative on failure + * + * Programmer: Quincey Koziol + * Wednesday, April 8, 2020 + * + *------------------------------------------------------------------------- + */ +herr_t +H5S__sel_iter_close_cb(H5S_sel_iter_t *_sel_iter, void H5_ATTR_UNUSED **request) +{ + H5S_sel_iter_t *sel_iter = (H5S_sel_iter_t *)_sel_iter; /* The selection iterator to close */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_PACKAGE + + /* Sanity check */ + HDassert(sel_iter); + + /* Close the selection iterator object */ + if (H5S_sel_iter_close(sel_iter) < 0) + HGOTO_ERROR(H5E_DATASPACE, H5E_CLOSEERROR, FAIL, "unable to close selection iterator"); + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5S__sel_iter_close_cb() */ + /*------------------------------------------------------------------------- * Function: H5S_sel_iter_close * diff --git a/test/tselect.c b/test/tselect.c index 612b927..1bfb663 100644 --- a/test/tselect.c +++ b/test/tselect.c @@ -15164,6 +15164,20 @@ test_sel_iter(void) iter_id = H5Ssel_iter_create(sid, (size_t)1, (unsigned)sel_iter_flags); CHECK(iter_id, FAIL, "H5Ssel_iter_create"); + /* Try resetting selection iterator with bad parameters */ + H5E_BEGIN_TRY + { + ret = H5Ssel_iter_reset(H5I_INVALID_HID, sid); + } + H5E_END_TRY; + VERIFY(ret, FAIL, "H5Ssel_iter_reset"); + H5E_BEGIN_TRY + { + ret = H5Ssel_iter_reset(iter_id, H5I_INVALID_HID); + } + H5E_END_TRY; + VERIFY(ret, FAIL, "H5Ssel_iter_reset"); + /* Try retrieving sequences, with bad parameters */ H5E_BEGIN_TRY { /* Invalid ID */ @@ -15314,6 +15328,167 @@ test_sel_iter(void) CHECK(ret, FAIL, "H5Ssel_iter_close"); } /* end for */ + /* Create selection iterator object */ + iter_id = H5Ssel_iter_create(sid, (size_t)1, (unsigned)sel_iter_flags); + CHECK(iter_id, FAIL, "H5Ssel_iter_create"); + + /* Test iterators on various basic selection types using + * H5Ssel_iter_reset instead of creating multiple iterators */ + for (sel_type = H5S_SEL_NONE; sel_type <= H5S_SEL_ALL; sel_type = (H5S_sel_type)(sel_type + 1)) { + switch (sel_type) { + case H5S_SEL_NONE: /* "None" selection */ + ret = H5Sselect_none(sid); + CHECK(ret, FAIL, "H5Sselect_none"); + break; + + case H5S_SEL_POINTS: /* Point selection */ + /* Select sequence of ten points */ + coord1[0][0] = 0; + coord1[0][1] = 9; + coord1[1][0] = 1; + coord1[1][1] = 2; + coord1[2][0] = 2; + coord1[2][1] = 4; + coord1[3][0] = 0; + coord1[3][1] = 6; + coord1[4][0] = 1; + coord1[4][1] = 8; + coord1[5][0] = 2; + coord1[5][1] = 10; + coord1[6][0] = 0; + coord1[6][1] = 11; + coord1[7][0] = 1; + coord1[7][1] = 4; + coord1[8][0] = 2; + coord1[8][1] = 1; + coord1[9][0] = 0; + coord1[9][1] = 3; + ret = H5Sselect_elements(sid, H5S_SELECT_SET, (size_t)POINT1_NPOINTS, + (const hsize_t *)coord1); + CHECK(ret, FAIL, "H5Sselect_elements"); + break; + + case H5S_SEL_HYPERSLABS: /* Hyperslab selection */ + /* Select regular hyperslab */ + start[0] = 3; + start[1] = 0; + stride[0] = 2; + stride[1] = 2; + count[0] = 2; + count[1] = 5; + block[0] = 1; + block[1] = 1; + ret = H5Sselect_hyperslab(sid, H5S_SELECT_SET, start, stride, count, block); + CHECK(ret, FAIL, "H5Sselect_hyperslab"); + break; + + case H5S_SEL_ALL: /* "All" selection */ + ret = H5Sselect_all(sid); + CHECK(ret, FAIL, "H5Sselect_all"); + break; + + case H5S_SEL_ERROR: + case H5S_SEL_N: + default: + HDassert(0 && "Can't occur"); + break; + } /* end switch */ + + /* Try retrieving no sequences, with 0 for maxseq & maxbytes */ + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)0, (size_t)1, &nseq, &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + VERIFY(nseq, 0, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 0, "H5Ssel_iter_get_seq_list"); + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)1, (size_t)0, &nseq, &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + VERIFY(nseq, 0, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 0, "H5Ssel_iter_get_seq_list"); + + /* Reset iterator */ + ret = H5Ssel_iter_reset(iter_id, sid); + CHECK(ret, FAIL, "H5Ssel_iter_reset"); + + /* Try retrieving all sequences */ + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)SEL_ITER_MAX_SEQ, (size_t)(1024 * 1024), &nseq, + &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + + /* Check results from retrieving sequence list */ + switch (sel_type) { + case H5S_SEL_NONE: /* "None" selection */ + VERIFY(nseq, 0, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 0, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_POINTS: /* Point selection */ + VERIFY(nseq, 10, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_HYPERSLABS: /* Hyperslab selection */ + VERIFY(nseq, 10, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_ALL: /* "All" selection */ + VERIFY(nseq, 1, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 72, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_ERROR: + case H5S_SEL_N: + default: + HDassert(0 && "Can't occur"); + break; + } /* end switch */ + + /* Reset iterator */ + ret = H5Ssel_iter_reset(iter_id, sid); + CHECK(ret, FAIL, "H5Ssel_iter_reset"); + + /* Try retrieving all sequences again */ + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)SEL_ITER_MAX_SEQ, (size_t)(1024 * 1024), &nseq, + &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + + /* Check results from retrieving sequence list */ + switch (sel_type) { + case H5S_SEL_NONE: /* "None" selection */ + VERIFY(nseq, 0, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 0, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_POINTS: /* Point selection */ + VERIFY(nseq, 10, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_HYPERSLABS: /* Hyperslab selection */ + VERIFY(nseq, 10, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_ALL: /* "All" selection */ + VERIFY(nseq, 1, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 72, "H5Ssel_iter_get_seq_list"); + break; + + case H5S_SEL_ERROR: + case H5S_SEL_N: + default: + HDassert(0 && "Can't occur"); + break; + } /* end switch */ + + /* Reset iterator */ + ret = H5Ssel_iter_reset(iter_id, sid); + CHECK(ret, FAIL, "H5Ssel_iter_reset"); + } /* end for */ + + /* Close selection iterator */ + ret = H5Ssel_iter_close(iter_id); + CHECK(ret, FAIL, "H5Ssel_iter_close"); + /* Point selection which will merge into smaller # of sequences */ coord1[0][0] = 0; coord1[0][1] = 9; @@ -15349,6 +15524,17 @@ test_sel_iter(void) VERIFY(nseq, 6, "H5Ssel_iter_get_seq_list"); VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + /* Reset iterator */ + ret = H5Ssel_iter_reset(iter_id, sid); + CHECK(ret, FAIL, "H5Ssel_iter_reset"); + + /* Try retrieving all sequences again */ + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)SEL_ITER_MAX_SEQ, (size_t)(1024 * 1024), &nseq, + &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + VERIFY(nseq, 6, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 10, "H5Ssel_iter_get_seq_list"); + /* Close selection iterator */ ret = H5Ssel_iter_close(iter_id); CHECK(ret, FAIL, "H5Ssel_iter_close"); @@ -15387,6 +15573,17 @@ test_sel_iter(void) VERIFY(nseq, 6, "H5Ssel_iter_get_seq_list"); VERIFY(nbytes, 20, "H5Ssel_iter_get_seq_list"); + /* Reset iterator */ + ret = H5Ssel_iter_reset(iter_id, sid); + CHECK(ret, FAIL, "H5Ssel_iter_reset"); + + /* Try retrieving all sequences again */ + ret = H5Ssel_iter_get_seq_list(iter_id, (size_t)SEL_ITER_MAX_SEQ, (size_t)(1024 * 1024), &nseq, + &nbytes, off, len); + CHECK(ret, FAIL, "H5Ssel_iter_get_seq_list"); + VERIFY(nseq, 6, "H5Ssel_iter_get_seq_list"); + VERIFY(nbytes, 20, "H5Ssel_iter_get_seq_list"); + /* Close selection iterator */ ret = H5Ssel_iter_close(iter_id); CHECK(ret, FAIL, "H5Ssel_iter_close"); |