[svn-r14307] Description:

- Extracted common code from H5D_select_read/H5D_select_write into single
        routine (H5D_select_io) and made H5D_select_read/H5D_select_write
        "gateway" routines, passing I/O buffer to operate on in "op" struct.
    - Create optimized pathway in H5D_select_io for I/O operations on single
        elements.
    - Make "get linear offset of first element" callback for each type of
        selection (used in "optimized pathway", above)

Tested on:
        FreeBSD/32 6.2 (duty) in debug mode
        FreeBSD/64 6.2 (liberty) w/C++ & FORTRAN, in debug mode
        Linux/32 2.6 (kagiso) w/PGI compilers, w/C++ & FORTRAN, w/threadsafe,
                                in debug mode
        Linux/64-amd64 2.6 (smirom) w/default API=1.6.x, w/C++ & FORTRAN,
                                in production mode
        Linux/64-ia64 2.6 (cobalt) w/Intel compilers, w/C++ & FORTRAN,
                                in production mode
        Solaris/32 2.10 (linew) w/deprecated symbols disabled, w/C++ & FORTRAN,
                                w/szip filter, in production mode
        Mac OS X/32 10.4.10 (amazon) in debug mode
        Linux/64-ia64 2.4 (tg-login3) w/parallel, w/FORTRAN, in production mode
This commit is contained in:
Quincey Koziol 2007-11-29 13:44:07 -05:00
parent 44fa94541b
commit 765f0159ff
9 changed files with 562 additions and 276 deletions

View File

@ -46,6 +46,18 @@
/* Local Prototypes */
/********************/
/* Struct for holding the vectorized I/O operation buffers "loosely" */
typedef struct {
enum {
H5S_SELECT_READ, /* Read selection */
H5S_SELECT_WRITE /* Write selection */
} op_type;
union {
void *rbuf; /* Buffer for read */
const void *wbuf; /* Buffer to write */
} u;
} H5D_select_buf_t;
/*********************/
/* Package Variables */
/*********************/
@ -417,6 +429,196 @@ done:
FUNC_LEAVE_NOAPI(ret_value);
} /* H5D_select_mgath() */
/*-------------------------------------------------------------------------
* Function: H5D_select_io
*
* Purpose: Perform I/O directly from application memory and a file
*
* Return: Non-negative on success/Negative on failure
*
* Programmer: Quincey Koziol
* Tuesday, November 27, 2007
*
*-------------------------------------------------------------------------
*/
static herr_t
H5D_select_io(H5D_io_info_t *io_info,
size_t nelmts, size_t elmt_size,
const H5S_t *file_space, const H5S_t *mem_space,
haddr_t addr, void *chunk/*in*/,
const H5D_select_buf_t *io_buf)
{
H5S_sel_iter_t mem_iter; /* Memory selection iteration info */
hbool_t mem_iter_init = 0; /* Memory selection iteration info has been initialized */
H5S_sel_iter_t file_iter; /* File selection iteration info */
hbool_t file_iter_init = 0; /* File selection iteration info has been initialized */
hsize_t _mem_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in memory */
hsize_t *mem_off = NULL; /* Pointer to sequence offsets in memory */
hsize_t _file_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in the file */
hsize_t *file_off = NULL; /* Pointer to sequence offsets in the file */
size_t _mem_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in memory */
size_t *mem_len = NULL; /* Pointer to sequence lengths in memory */
size_t _file_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in the file */
size_t *file_len = NULL; /* Pointer to sequence lengths in the file */
size_t curr_mem_seq; /* Current memory sequence to operate on */
size_t curr_file_seq; /* Current file sequence to operate on */
size_t mem_nseq; /* Number of sequences generated in the file */
size_t file_nseq; /* Number of sequences generated in memory */
ssize_t tmp_file_len; /* Temporary number of bytes in file sequence */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI(H5D_select_io, FAIL)
/* Check args */
HDassert(io_info);
HDassert(io_info->dset);
HDassert(io_info->store);
HDassert(TRUE == H5P_isa_class(io_info->dxpl_id, H5P_DATASET_XFER));
HDassert(io_buf->u.rbuf);
/* Allocate the vector I/O arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if(NULL == (mem_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size)))
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array")
if(NULL == (mem_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size)))
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array")
if(NULL == (file_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size)))
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array")
if(NULL == (file_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size)))
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array")
} /* end if */
else {
mem_len = _mem_len;
mem_off = _mem_off;
file_len = _file_len;
file_off = _file_off;
} /* end else */
/* Check for only one element in selection */
if(nelmts == 1) {
/* Get offset of first element in selections */
if(H5S_SELECT_OFFSET(file_space, file_off) < 0)
HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "can't retrieve file selection offset")
if(H5S_SELECT_OFFSET(mem_space, mem_off) < 0)
HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "can't retrieve memory selection offset")
/* Set up necessary information for I/O operation */
file_nseq = mem_nseq = 1;
curr_mem_seq = curr_file_seq = 0;
*file_off *= elmt_size;
*mem_off *= elmt_size;
*file_len = *mem_len = elmt_size;
/* Perform I/O on memory and file sequences */
if(io_buf->op_type == H5S_SELECT_READ) {
if((tmp_file_len = (*io_info->ops.readvv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, io_buf->u.rbuf)) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_READERROR, FAIL, "read error")
} /* end if */
else {
HDassert(io_buf->op_type == H5S_SELECT_WRITE);
if((tmp_file_len = (*io_info->ops.writevv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, io_buf->u.wbuf)) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_WRITEERROR, FAIL, "write error")
} /* end else */
/* Decrement number of elements left to process */
HDassert((tmp_file_len % elmt_size) == 0);
} /* end if */
else {
size_t mem_nelem; /* Number of elements used in memory sequences */
size_t file_nelem; /* Number of elements used in file sequences */
/* Initialize file iterator */
if(H5S_select_iter_init(&file_iter, file_space, elmt_size) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator")
file_iter_init = 1; /* File selection iteration info has been initialized */
/* Initialize memory iterator */
if(H5S_select_iter_init(&mem_iter, mem_space, elmt_size) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator")
mem_iter_init = 1; /* Memory selection iteration info has been initialized */
/* Initialize sequence counts */
curr_mem_seq = curr_file_seq = 0;
mem_nseq = file_nseq = 0;
/* Loop, until all bytes are processed */
while(nelmts > 0) {
/* Check if more file sequences are needed */
if(curr_file_seq >= file_nseq) {
/* Get sequences for file selection */
if(H5S_SELECT_GET_SEQ_LIST(file_space, H5S_GET_SEQ_LIST_SORTED, &file_iter, io_info->dxpl_cache->vec_size, nelmts, &file_nseq, &file_nelem, file_off, file_len) < 0)
HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed")
/* Start at the beginning of the sequences again */
curr_file_seq = 0;
} /* end if */
/* Check if more memory sequences are needed */
if(curr_mem_seq >= mem_nseq) {
/* Get sequences for memory selection */
if(H5S_SELECT_GET_SEQ_LIST(mem_space, 0, &mem_iter, io_info->dxpl_cache->vec_size, nelmts, &mem_nseq, &mem_nelem, mem_off, mem_len) < 0)
HGOTO_ERROR(H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed")
/* Start at the beginning of the sequences again */
curr_mem_seq = 0;
} /* end if */
/* Perform I/O on memory and file sequences */
if(io_buf->op_type == H5S_SELECT_READ) {
if((tmp_file_len = (*io_info->ops.readvv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, io_buf->u.rbuf)) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_READERROR, FAIL, "read error")
} /* end if */
else {
HDassert(io_buf->op_type == H5S_SELECT_WRITE);
if((tmp_file_len = (*io_info->ops.writevv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, io_buf->u.wbuf)) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_WRITEERROR, FAIL, "write error")
} /* end else */
/* Decrement number of elements left to process */
HDassert((tmp_file_len % elmt_size) == 0);
nelmts -= (tmp_file_len / elmt_size);
} /* end while */
} /* end else */
done:
/* Release file selection iterator */
if(file_iter_init)
if(H5S_SELECT_ITER_RELEASE(&file_iter) < 0)
HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator")
/* Release memory selection iterator */
if(mem_iter_init)
if(H5S_SELECT_ITER_RELEASE(&mem_iter) < 0)
HDONE_ERROR(H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator")
/* Free vector arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if(file_len != NULL)
H5FL_SEQ_FREE(size_t, file_len);
if(file_off != NULL)
H5FL_SEQ_FREE(hsize_t, file_off);
if(mem_len != NULL)
H5FL_SEQ_FREE(size_t, mem_len);
if(mem_off != NULL)
H5FL_SEQ_FREE(hsize_t, mem_off);
} /* end if */
FUNC_LEAVE_NOAPI(ret_value)
} /* end H5D_select_io() */
/*-------------------------------------------------------------------------
* Function: H5D_select_read
@ -437,128 +639,21 @@ H5D_select_read(H5D_io_info_t *io_info,
haddr_t addr, void *chunk/*in*/,
void *buf/*out*/)
{
H5S_sel_iter_t mem_iter; /* Memory selection iteration info */
hbool_t mem_iter_init=0; /* Memory selection iteration info has been initialized */
H5S_sel_iter_t file_iter; /* File selection iteration info */
hbool_t file_iter_init=0; /* File selection iteration info has been initialized */
hsize_t _mem_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in memory */
hsize_t *mem_off=NULL; /* Pointer to sequence offsets in memory */
hsize_t _file_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in the file */
hsize_t *file_off=NULL; /* Pointer to sequence offsets in the file */
size_t _mem_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in memory */
size_t *mem_len=NULL; /* Pointer to sequence lengths in memory */
size_t _file_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in the file */
size_t *file_len=NULL; /* Pointer to sequence lengths in the file */
size_t mem_nseq; /* Number of sequences generated in the file */
size_t file_nseq; /* Number of sequences generated in memory */
size_t mem_nelem; /* Number of elements used in memory sequences */
size_t file_nelem; /* Number of elements used in file sequences */
size_t curr_mem_seq; /* Current memory sequence to operate on */
size_t curr_file_seq; /* Current file sequence to operate on */
ssize_t tmp_file_len; /* Temporary number of bytes in file sequence */
herr_t ret_value=SUCCEED; /* Return value */
H5D_select_buf_t io_buf; /* Selection I/O operation to perform */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI(H5D_select_read, FAIL);
FUNC_ENTER_NOAPI(H5D_select_read, FAIL)
/* Check args */
assert(io_info);
assert(io_info->dset);
assert(io_info->dxpl_cache);
assert(io_info->store);
assert(buf);
assert(TRUE==H5P_isa_class(io_info->dxpl_id,H5P_DATASET_XFER));
/* Construct proper I/O operation */
io_buf.op_type = H5S_SELECT_READ;
io_buf.u.rbuf = buf;
/* Initialize file iterator */
if (H5S_select_iter_init(&file_iter, file_space, elmt_size)<0)
HGOTO_ERROR (H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator");
file_iter_init=1; /* File selection iteration info has been initialized */
/* Initialize memory iterator */
if (H5S_select_iter_init(&mem_iter, mem_space, elmt_size)<0)
HGOTO_ERROR (H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator");
mem_iter_init=1; /* Memory selection iteration info has been initialized */
/* Allocate the vector I/O arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if((mem_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array");
if((mem_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array");
if((file_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array");
if((file_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array");
} /* end if */
else {
mem_len=_mem_len;
mem_off=_mem_off;
file_len=_file_len;
file_off=_file_off;
} /* end else */
/* Initialize sequence counts */
curr_mem_seq=curr_file_seq=0;
mem_nseq=file_nseq=0;
/* Loop, until all bytes are processed */
while(nelmts>0) {
/* Check if more file sequences are needed */
if(curr_file_seq>=file_nseq) {
/* Get sequences for file selection */
if(H5S_SELECT_GET_SEQ_LIST(file_space,H5S_GET_SEQ_LIST_SORTED,&file_iter,io_info->dxpl_cache->vec_size,nelmts,&file_nseq,&file_nelem,file_off,file_len)<0)
HGOTO_ERROR (H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed");
/* Start at the beginning of the sequences again */
curr_file_seq=0;
} /* end if */
/* Check if more memory sequences are needed */
if(curr_mem_seq>=mem_nseq) {
/* Get sequences for memory selection */
if(H5S_SELECT_GET_SEQ_LIST(mem_space,0,&mem_iter,io_info->dxpl_cache->vec_size,nelmts,&mem_nseq,&mem_nelem,mem_off,mem_len)<0)
HGOTO_ERROR (H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed");
/* Start at the beginning of the sequences again */
curr_mem_seq=0;
} /* end if */
/* Read file sequences into current memory sequence */
if ((tmp_file_len=(*io_info->ops.readvv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, buf))<0)
HGOTO_ERROR(H5E_DATASPACE, H5E_READERROR, FAIL, "read error");
/* Decrement number of elements left to process */
assert((tmp_file_len%elmt_size)==0);
nelmts-=(tmp_file_len/elmt_size);
} /* end while */
/* Call generic selection operation */
if(H5D_select_io(io_info, nelmts, elmt_size, file_space, mem_space, addr, chunk, &io_buf) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_READERROR, FAIL, "read error")
done:
/* Release file selection iterator */
if(file_iter_init) {
if (H5S_SELECT_ITER_RELEASE(&file_iter)<0)
HDONE_ERROR (H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator");
} /* end if */
/* Release memory selection iterator */
if(mem_iter_init) {
if (H5S_SELECT_ITER_RELEASE(&mem_iter)<0)
HDONE_ERROR (H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator");
} /* end if */
/* Free vector arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if(file_len!=NULL)
H5FL_SEQ_FREE(size_t,file_len);
if(file_off!=NULL)
H5FL_SEQ_FREE(hsize_t,file_off);
if(mem_len!=NULL)
H5FL_SEQ_FREE(size_t,mem_len);
if(mem_off!=NULL)
H5FL_SEQ_FREE(hsize_t,mem_off);
} /* end if */
FUNC_LEAVE_NOAPI(ret_value);
FUNC_LEAVE_NOAPI(ret_value)
} /* end H5D_select_read() */
@ -581,127 +676,20 @@ H5D_select_write(H5D_io_info_t *io_info,
haddr_t addr, void *chunk/*in*/,
const void *buf/*out*/)
{
H5S_sel_iter_t mem_iter; /* Memory selection iteration info */
hbool_t mem_iter_init=0; /* Memory selection iteration info has been initialized */
H5S_sel_iter_t file_iter; /* File selection iteration info */
hbool_t file_iter_init=0; /* File selection iteration info has been initialized */
hsize_t _mem_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in memory */
hsize_t *mem_off=NULL; /* Pointer to sequence offsets in memory */
hsize_t _file_off[H5D_IO_VECTOR_SIZE]; /* Array to store sequence offsets in the file */
hsize_t *file_off=NULL; /* Pointer to sequence offsets in the file */
size_t _mem_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in memory */
size_t *mem_len=NULL; /* Pointer to sequence lengths in memory */
size_t _file_len[H5D_IO_VECTOR_SIZE]; /* Array to store sequence lengths in the file */
size_t *file_len=NULL; /* Pointer to sequence lengths in the file */
size_t mem_nseq; /* Number of sequences generated in the file */
size_t file_nseq; /* Number of sequences generated in memory */
size_t mem_nelem; /* Number of elements used in memory sequences */
size_t file_nelem; /* Number of elements used in file sequences */
size_t curr_mem_seq; /* Current memory sequence to operate on */
size_t curr_file_seq; /* Current file sequence to operate on */
ssize_t tmp_file_len; /* Temporary number of bytes in file sequence */
herr_t ret_value=SUCCEED; /* Return value */
H5D_select_buf_t io_buf; /* Selection I/O operation to perform */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI(H5D_select_write, FAIL);
FUNC_ENTER_NOAPI(H5D_select_write, FAIL)
/* Check args */
assert(io_info);
assert(io_info->dset);
assert(io_info->store);
assert(TRUE==H5P_isa_class(io_info->dxpl_id,H5P_DATASET_XFER));
assert(buf);
/* Construct proper I/O operation */
io_buf.op_type = H5S_SELECT_WRITE;
io_buf.u.wbuf = buf;
/* Allocate the vector I/O arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if((mem_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array");
if((mem_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array");
if((file_len = H5FL_SEQ_MALLOC(size_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O length vector array");
if((file_off = H5FL_SEQ_MALLOC(hsize_t,io_info->dxpl_cache->vec_size))==NULL)
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "can't allocate I/O offset vector array");
} /* end if */
else {
mem_len=_mem_len;
mem_off=_mem_off;
file_len=_file_len;
file_off=_file_off;
} /* end else */
/* Initialize file iterator */
if (H5S_select_iter_init(&file_iter, file_space, elmt_size)<0)
HGOTO_ERROR (H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator");
file_iter_init=1; /* File selection iteration info has been initialized */
/* Initialize memory iterator */
if (H5S_select_iter_init(&mem_iter, mem_space, elmt_size)<0)
HGOTO_ERROR (H5E_DATASPACE, H5E_CANTINIT, FAIL, "unable to initialize selection iterator");
mem_iter_init=1; /* Memory selection iteration info has been initialized */
/* Initialize sequence counts */
curr_mem_seq=curr_file_seq=0;
mem_nseq=file_nseq=0;
/* Loop, until all bytes are processed */
while(nelmts>0) {
/* Check if more file sequences are needed */
if(curr_file_seq>=file_nseq) {
/* Get sequences for file selection */
if(H5S_SELECT_GET_SEQ_LIST(file_space,H5S_GET_SEQ_LIST_SORTED,&file_iter,io_info->dxpl_cache->vec_size,nelmts,&file_nseq,&file_nelem,file_off,file_len)<0)
HGOTO_ERROR (H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed");
/* Start at the beginning of the sequences again */
curr_file_seq=0;
} /* end if */
/* Check if more memory sequences are needed */
if(curr_mem_seq>=mem_nseq) {
/* Get sequences for memory selection */
if(H5S_SELECT_GET_SEQ_LIST(mem_space,0,&mem_iter,io_info->dxpl_cache->vec_size,nelmts,&mem_nseq,&mem_nelem,mem_off,mem_len)<0)
HGOTO_ERROR (H5E_INTERNAL, H5E_UNSUPPORTED, FAIL, "sequence length generation failed");
/* Start at the beginning of the sequences again */
curr_mem_seq=0;
} /* end if */
/* Write memory sequences into file sequences */
if ((tmp_file_len=(*io_info->ops.writevv)(io_info,
file_nseq, &curr_file_seq, file_len, file_off,
mem_nseq, &curr_mem_seq, mem_len, mem_off,
addr, chunk, buf))<0)
HGOTO_ERROR(H5E_DATASPACE, H5E_WRITEERROR, FAIL, "write error");
/* Decrement number of elements left to process */
assert((tmp_file_len%elmt_size)==0);
nelmts-=(tmp_file_len/elmt_size);
} /* end while */
/* Call generic selection operation */
if(H5D_select_io(io_info, nelmts, elmt_size, file_space, mem_space, addr, chunk, &io_buf) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_WRITEERROR, FAIL, "write error")
done:
/* Release file selection iterator */
if(file_iter_init) {
if (H5S_SELECT_ITER_RELEASE(&file_iter)<0)
HDONE_ERROR (H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator");
} /* end if */
/* Release memory selection iterator */
if(mem_iter_init) {
if (H5S_SELECT_ITER_RELEASE(&mem_iter)<0)
HDONE_ERROR (H5E_DATASPACE, H5E_CANTRELEASE, FAIL, "unable to release selection iterator");
} /* end if */
/* Free vector arrays */
if(io_info->dxpl_cache->vec_size != H5D_IO_VECTOR_SIZE) {
if(file_len!=NULL)
H5FL_SEQ_FREE(size_t,file_len);
if(file_off!=NULL)
H5FL_SEQ_FREE(hsize_t,file_off);
if(mem_len!=NULL)
H5FL_SEQ_FREE(size_t,mem_len);
if(mem_off!=NULL)
H5FL_SEQ_FREE(hsize_t,mem_off);
} /* end if */
FUNC_LEAVE_NOAPI(ret_value);
FUNC_LEAVE_NOAPI(ret_value)
} /* end H5D_select_write() */

View File

@ -42,6 +42,7 @@ static hssize_t H5S_all_serial_size(const H5S_t *space);
static herr_t H5S_all_serialize(const H5S_t *space, uint8_t *buf);
static herr_t H5S_all_deserialize(H5S_t *space, const uint8_t *buf);
static herr_t H5S_all_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
static herr_t H5S_all_offset(const H5S_t *space, hsize_t *off);
static htri_t H5S_all_is_contiguous(const H5S_t *space);
static htri_t H5S_all_is_single(const H5S_t *space);
static htri_t H5S_all_is_regular(const H5S_t *space);
@ -70,6 +71,7 @@ const H5S_select_class_t H5S_sel_all[1] = {{
H5S_all_serialize,
H5S_all_deserialize,
H5S_all_bounds,
H5S_all_offset,
H5S_all_is_contiguous,
H5S_all_is_single,
H5S_all_is_regular,
@ -585,26 +587,61 @@ done:
herr_t
H5S_all_bounds(const H5S_t *space, hsize_t *start, hsize_t *end)
{
int rank; /* Dataspace rank */
int i; /* index variable */
unsigned rank; /* Dataspace rank */
unsigned i; /* index variable */
FUNC_ENTER_NOAPI_NOFUNC(H5S_all_bounds);
FUNC_ENTER_NOAPI_NOFUNC(H5S_all_bounds)
assert(space);
assert(start);
assert(end);
HDassert(space);
HDassert(start);
HDassert(end);
/* Get the dataspace extent rank */
rank=space->extent.rank;
rank = space->extent.rank;
/* Just copy over the complete extent */
for(i=0; i<rank; i++) {
start[i]=0;
end[i]=space->extent.size[i]-1;
for(i = 0; i < rank; i++) {
start[i] = 0;
end[i] = space->extent.size[i] - 1;
} /* end for */
FUNC_LEAVE_NOAPI(SUCCEED);
} /* H5Sget_all_bounds() */
FUNC_LEAVE_NOAPI(SUCCEED)
} /* H5S_all_bounds() */
/*--------------------------------------------------------------------------
NAME
H5S_all_offset
PURPOSE
Gets the linear offset of the first element for the selection.
USAGE
herr_t H5S_all_offset(space, offset)
const H5S_t *space; IN: Dataspace pointer of selection to query
hsize_t *offset; OUT: Linear offset of first element in selection
RETURNS
Non-negative on success, negative on failure
DESCRIPTION
Retrieves the linear offset (in "units" of elements) of the first element
selected within the dataspace.
GLOBAL VARIABLES
COMMENTS, BUGS, ASSUMPTIONS
Calling this function on a "none" selection returns fail.
EXAMPLES
REVISION LOG
--------------------------------------------------------------------------*/
herr_t
H5S_all_offset(const H5S_t *space, hsize_t *offset)
{
FUNC_ENTER_NOAPI_NOFUNC(H5S_all_offset)
HDassert(space);
HDassert(offset);
/* 'All' selections always start at offset 0 */
*offset = 0;
FUNC_LEAVE_NOAPI(SUCCEED)
} /* H5S_all_offset() */
/*--------------------------------------------------------------------------

View File

@ -57,6 +57,7 @@ static hssize_t H5S_hyper_serial_size(const H5S_t *space);
static herr_t H5S_hyper_serialize(const H5S_t *space, uint8_t *buf);
static herr_t H5S_hyper_deserialize(H5S_t *space, const uint8_t *buf);
static herr_t H5S_hyper_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
static herr_t H5S_hyper_offset(const H5S_t *space, hsize_t *offset);
static htri_t H5S_hyper_is_contiguous(const H5S_t *space);
static htri_t H5S_hyper_is_single(const H5S_t *space);
static htri_t H5S_hyper_is_regular(const H5S_t *space);
@ -90,6 +91,7 @@ const H5S_select_class_t H5S_sel_hyper[1] = {{
H5S_hyper_serialize,
H5S_hyper_deserialize,
H5S_hyper_bounds,
H5S_hyper_offset,
H5S_hyper_is_contiguous,
H5S_hyper_is_single,
H5S_hyper_is_regular,
@ -2705,6 +2707,114 @@ done:
FUNC_LEAVE_NOAPI(ret_value)
} /* H5S_hyper_bounds() */
/*--------------------------------------------------------------------------
NAME
H5S_hyper_offset
PURPOSE
Gets the linear offset of the first element for the selection.
USAGE
herr_t H5S_hyper_offset(space, offset)
const H5S_t *space; IN: Dataspace pointer of selection to query
hsize_t *offset; OUT: Linear offset of first element in selection
RETURNS
Non-negative on success, negative on failure
DESCRIPTION
Retrieves the linear offset (in "units" of elements) of the first element
selected within the dataspace.
GLOBAL VARIABLES
COMMENTS, BUGS, ASSUMPTIONS
Calling this function on a "none" selection returns fail.
EXAMPLES
REVISION LOG
--------------------------------------------------------------------------*/
herr_t
H5S_hyper_offset(const H5S_t *space, hsize_t *offset)
{
const hssize_t *sel_offset; /* Pointer to the selection's offset */
const hsize_t *dim_size; /* Pointer to a dataspace's extent */
hsize_t accum; /* Accumulator for dimension sizes */
int rank; /* Dataspace rank */
int i; /* index variable */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI(H5S_hyper_offset, FAIL)
HDassert(space);
HDassert(offset);
/* Start at linear offset 0 */
*offset = 0;
/* Set up pointers to arrays of values */
rank = space->extent.rank;
sel_offset = space->select.offset;
dim_size = space->extent.size;
/* Check for a "regular" hyperslab selection */
if(space->select.sel_info.hslab->diminfo_valid) {
const H5S_hyper_dim_t *diminfo = space->select.sel_info.hslab->opt_diminfo; /* Local alias for diminfo */
/* Loop through starting coordinates, calculating the linear offset */
accum = 1;
for(i = (rank - 1); i >= 0; i--) {
hssize_t hyp_offset = (hssize_t)diminfo[i].start + sel_offset[i]; /* Hyperslab's offset in this dimension */
/* Check for offset moving selection out of the dataspace */
if(hyp_offset < 0 || (hsize_t)hyp_offset >= dim_size[i])
HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "offset moves selection out of bounds")
/* Add the hyperslab's offset in this dimension to the total linear offset */
*offset += hyp_offset * accum;
/* Increase the accumulator */
accum *= dim_size[i];
} /* end for */
} /* end if */
else {
const H5S_hyper_span_t *span; /* Hyperslab span node */
hsize_t dim_accum[H5S_MAX_RANK]; /* Accumulators, for each dimension */
/* Calculate the accumulator for each dimension */
accum = 1;
for(i = (rank - 1); i >= 0; i--) {
/* Set the accumulator for this dimension */
dim_accum[i] = accum;
/* Increase the accumulator */
accum *= dim_size[i];
} /* end for */
/* Get information for the first span, in the slowest changing dimension */
span = space->select.sel_info.hslab->span_lst->head;
/* Work down the spans, computing the linear offset */
i = 0;
while(span) {
hssize_t hyp_offset = (hssize_t)span->low + sel_offset[i]; /* Hyperslab's offset in this dimension */
/* Check for offset moving selection out of the dataspace */
if(hyp_offset < 0 || (hsize_t)hyp_offset >= dim_size[i])
HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "offset moves selection out of bounds")
/* Add the hyperslab's offset in this dimension to the total linear offset */
*offset += hyp_offset * dim_accum[i];
/* Advance to first span in "down" dimension */
if(span->down) {
HDassert(span->down->head);
span = span->down->head;
} /* end if */
else
span = NULL;
i++;
} /* end while */
} /* end else */
done:
FUNC_LEAVE_NOAPI(ret_value)
} /* H5S_hyper_offset() */
/*--------------------------------------------------------------------------
NAME
@ -2727,12 +2837,10 @@ done:
htri_t
H5S_hyper_is_contiguous(const H5S_t *space)
{
H5S_hyper_span_info_t *spans; /* Hyperslab span info node */
H5S_hyper_span_t *span; /* Hyperslab span node */
unsigned u; /* index variable */
unsigned small_contiguous, /* Flag for small contiguous block */
large_contiguous; /* Flag for large contiguous block */
htri_t ret_value=FALSE; /* return value */
unsigned u; /* index variable */
htri_t ret_value = FALSE; /* Return value */
FUNC_ENTER_NOAPI_NOFUNC(H5S_hyper_is_contiguous);
@ -2791,6 +2899,9 @@ H5S_hyper_is_contiguous(const H5S_t *space)
ret_value=TRUE;
} /* end if */
else {
H5S_hyper_span_info_t *spans; /* Hyperslab span info node */
H5S_hyper_span_t *span; /* Hyperslab span node */
/*
* For a hyperslab to be contiguous, it must have only one block and
* (either it's size must be the same as the dataspace extent's in all

View File

@ -43,6 +43,7 @@ static hssize_t H5S_none_serial_size(const H5S_t *space);
static herr_t H5S_none_serialize(const H5S_t *space, uint8_t *buf);
static herr_t H5S_none_deserialize(H5S_t *space, const uint8_t *buf);
static herr_t H5S_none_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
static herr_t H5S_none_offset(const H5S_t *space, hsize_t *off);
static htri_t H5S_none_is_contiguous(const H5S_t *space);
static htri_t H5S_none_is_single(const H5S_t *space);
static htri_t H5S_none_is_regular(const H5S_t *space);
@ -71,6 +72,7 @@ const H5S_select_class_t H5S_sel_none[1] = {{
H5S_none_serialize,
H5S_none_deserialize,
H5S_none_bounds,
H5S_none_offset,
H5S_none_is_contiguous,
H5S_none_is_single,
H5S_none_is_regular,
@ -562,6 +564,38 @@ H5S_none_bounds(const H5S_t UNUSED *space, hsize_t UNUSED *start, hsize_t UNUSED
FUNC_LEAVE_NOAPI(FAIL);
} /* H5Sget_none_bounds() */
/*--------------------------------------------------------------------------
NAME
H5S_none_offset
PURPOSE
Gets the linear offset of the first element for the selection.
USAGE
herr_t H5S_none_offset(space, offset)
const H5S_t *space; IN: Dataspace pointer of selection to query
hsize_t *offset; OUT: Linear offset of first element in selection
RETURNS
Non-negative on success, negative on failure
DESCRIPTION
Retrieves the linear offset (in "units" of elements) of the first element
selected within the dataspace.
GLOBAL VARIABLES
COMMENTS, BUGS, ASSUMPTIONS
Calling this function on a "none" selection returns fail.
EXAMPLES
REVISION LOG
--------------------------------------------------------------------------*/
herr_t
H5S_none_offset(const H5S_t *space, hsize_t *offset)
{
FUNC_ENTER_NOAPI_NOFUNC(H5S_none_offset)
HDassert(space);
HDassert(offset);
FUNC_LEAVE_NOAPI(FAIL)
} /* H5S_none_offset() */
/*--------------------------------------------------------------------------
NAME
@ -569,7 +603,7 @@ H5S_none_bounds(const H5S_t UNUSED *space, hsize_t UNUSED *start, hsize_t UNUSED
PURPOSE
Check if a "none" selection is contiguous within the dataspace extent.
USAGE
htri_t H5S_all_is_contiguous(space)
htri_t H5S_none_is_contiguous(space)
H5S_t *space; IN: Dataspace pointer to check
RETURNS
TRUE/FALSE/FAIL
@ -767,7 +801,7 @@ done:
PURPOSE
Create a list of offsets & lengths for a selection
USAGE
herr_t H5S_all_get_seq_list(space,flags,iter,maxseq,maxelem,nseq,nelem,off,len)
herr_t H5S_none_get_seq_list(space,flags,iter,maxseq,maxelem,nseq,nelem,off,len)
H5S_t *space; IN: Dataspace containing selection to use.
unsigned flags; IN: Flags for extra information about operation
H5S_sel_iter_t *iter; IN/OUT: Selection iterator describing last
@ -816,4 +850,5 @@ H5S_none_get_seq_list(const H5S_t UNUSED *space, unsigned UNUSED flags, H5S_sel_
*nelem=0;
FUNC_LEAVE_NOAPI(SUCCEED);
} /* end H5S_all_get_seq_list() */
} /* end H5S_none_get_seq_list() */

View File

@ -133,8 +133,10 @@ typedef hssize_t (*H5S_sel_serial_size_func_t)(const H5S_t *space);
typedef herr_t (*H5S_sel_serialize_func_t)(const H5S_t *space, uint8_t *buf);
/* Method to store create selection from "serialized" form (a byte sequence suitable for storing on disk) */
typedef herr_t (*H5S_sel_deserialize_func_t)(H5S_t *space, const uint8_t *buf);
/* Method to determine to smallest n-D bounding box containing the current selection */
/* Method to determine smallest n-D bounding box containing the current selection */
typedef herr_t (*H5S_sel_bounds_func_t)(const H5S_t *space, hsize_t *start, hsize_t *end);
/* Method to determine linear offset of initial element in selection within dataspace */
typedef herr_t (*H5S_sel_offset_func_t)(const H5S_t *space, hsize_t *offset);
/* Method to determine if current selection is contiguous */
typedef htri_t (*H5S_sel_is_contiguous_func_t)(const H5S_t *space);
/* Method to determine if current selection is a single block */
@ -159,6 +161,7 @@ typedef struct {
H5S_sel_serialize_func_t serialize; /* Method to store current selection in "serialized" form (a byte sequence suitable for storing on disk) */
H5S_sel_deserialize_func_t deserialize; /* Method to store create selection from "serialized" form (a byte sequence suitable for storing on disk) */
H5S_sel_bounds_func_t bounds; /* Method to determine to smallest n-D bounding box containing the current selection */
H5S_sel_offset_func_t offset; /* Method to determine linear offset of initial element in selection within dataspace */
H5S_sel_is_contiguous_func_t is_contiguous; /* Method to determine if current selection is contiguous */
H5S_sel_is_single_func_t is_single; /* Method to determine if current selection is a single block */
H5S_sel_is_regular_func_t is_regular; /* Method to determine if current selection is "regular" */

View File

@ -44,6 +44,7 @@ static hssize_t H5S_point_serial_size(const H5S_t *space);
static herr_t H5S_point_serialize(const H5S_t *space, uint8_t *buf);
static herr_t H5S_point_deserialize(H5S_t *space, const uint8_t *buf);
static herr_t H5S_point_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
static herr_t H5S_point_offset(const H5S_t *space, hsize_t *off);
static htri_t H5S_point_is_contiguous(const H5S_t *space);
static htri_t H5S_point_is_single(const H5S_t *space);
static htri_t H5S_point_is_regular(const H5S_t *space);
@ -72,6 +73,7 @@ const H5S_select_class_t H5S_sel_point[1] = {{
H5S_point_serialize,
H5S_point_deserialize,
H5S_point_bounds,
H5S_point_offset,
H5S_point_is_contiguous,
H5S_point_is_single,
H5S_point_is_regular,
@ -1038,45 +1040,111 @@ static herr_t
H5S_point_bounds(const H5S_t *space, hsize_t *start, hsize_t *end)
{
H5S_pnt_node_t *node; /* Point node */
int rank; /* Dataspace rank */
int i; /* index variable */
herr_t ret_value=SUCCEED; /* Return value */
unsigned rank; /* Dataspace rank */
unsigned u; /* index variable */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI_NOINIT(H5S_point_bounds);
FUNC_ENTER_NOAPI_NOINIT(H5S_point_bounds)
assert(space);
assert(start);
assert(end);
HDassert(space);
HDassert(start);
HDassert(end);
/* Get the dataspace extent rank */
rank=space->extent.rank;
rank = space->extent.rank;
/* Set the start and end arrays up */
for(i=0; i<rank; i++) {
start[i]=HSIZET_MAX;
end[i]=0;
for(u = 0; u < rank; u++) {
start[u] = HSIZET_MAX;
end[u] = 0;
} /* end for */
/* Iterate through the node, checking the bounds on each element */
node=space->select.sel_info.pnt_lst->head;
while(node!=NULL) {
for(i=0; i<rank; i++) {
node = space->select.sel_info.pnt_lst->head;
while(node != NULL) {
for(u = 0; u < rank; u++) {
/* Check for offset moving selection negative */
if(((hssize_t)node->pnt[i]+space->select.offset[i])<0)
if(((hssize_t)node->pnt[u] + space->select.offset[u]) < 0)
HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "offset moves selection out of bounds")
if(start[i]>(node->pnt[i]+space->select.offset[i]))
start[i]=node->pnt[i]+space->select.offset[i];
if(end[i]<(node->pnt[i]+space->select.offset[i]))
end[i]=node->pnt[i]+space->select.offset[i];
if(start[u] > (node->pnt[u] + space->select.offset[u]))
start[u] = node->pnt[u] + space->select.offset[u];
if(end[u] < (node->pnt[u] + space->select.offset[u]))
end[u] = node->pnt[u] + space->select.offset[u];
} /* end for */
node=node->next;
node = node->next;
} /* end while */
done:
FUNC_LEAVE_NOAPI(ret_value);
FUNC_LEAVE_NOAPI(ret_value)
} /* H5S_point_bounds() */
/*--------------------------------------------------------------------------
NAME
H5S_point_offset
PURPOSE
Gets the linear offset of the first element for the selection.
USAGE
herr_t H5S_point_offset(space, offset)
const H5S_t *space; IN: Dataspace pointer of selection to query
hsize_t *offset; OUT: Linear offset of first element in selection
RETURNS
Non-negative on success, negative on failure
DESCRIPTION
Retrieves the linear offset (in "units" of elements) of the first element
selected within the dataspace.
GLOBAL VARIABLES
COMMENTS, BUGS, ASSUMPTIONS
Calling this function on a "none" selection returns fail.
EXAMPLES
REVISION LOG
--------------------------------------------------------------------------*/
herr_t
H5S_point_offset(const H5S_t *space, hsize_t *offset)
{
const hsize_t *pnt; /* Pointer to a selected point's coordinates */
const hssize_t *sel_offset; /* Pointer to the selection's offset */
const hsize_t *dim_size; /* Pointer to a dataspace's extent */
hsize_t accum; /* Accumulator for dimension sizes */
int rank; /* Dataspace rank */
int i; /* index variable */
herr_t ret_value = SUCCEED; /* Return value */
FUNC_ENTER_NOAPI(H5S_point_offset, FAIL)
HDassert(space);
HDassert(offset);
/* Start at linear offset 0 */
*offset = 0;
/* Set up pointers to arrays of values */
pnt = space->select.sel_info.pnt_lst->head->pnt;
sel_offset = space->select.offset;
dim_size = space->extent.size;
/* Loop through coordinates, calculating the linear offset */
rank = space->extent.rank;
accum = 1;
for(i = (rank - 1); i >= 0; i--) {
hssize_t pnt_offset = (hssize_t)pnt[i] + sel_offset[i]; /* Point's offset in this dimension */
/* Check for offset moving selection out of the dataspace */
if(pnt_offset < 0 || (hsize_t)pnt_offset >= dim_size[i])
HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "offset moves selection out of bounds")
/* Add the point's offset in this dimension to the total linear offset */
*offset += pnt_offset * accum;
/* Increase the accumulator */
accum *= dim_size[i];
} /* end for */
done:
FUNC_LEAVE_NOAPI(ret_value)
} /* H5S_point_offset() */
/*--------------------------------------------------------------------------
NAME

View File

@ -152,6 +152,7 @@ typedef struct H5S_iostats_t {
#define H5S_SELECT_SERIAL_SIZE(S) ((*(S)->select.type->serial_size)(S))
#define H5S_SELECT_SERIALIZE(S,BUF) ((*(S)->select.type->serialize)(S,BUF))
#define H5S_SELECT_BOUNDS(S,START,END) ((*(S)->select.type->bounds)(S,START,END))
#define H5S_SELECT_OFFSET(S, OFFSET) ((*(S)->select.type->offset)(S, OFFSET))
#define H5S_SELECT_IS_CONTIGUOUS(S) ((*(S)->select.type->is_contiguous)(S))
#define H5S_SELECT_IS_SINGLE(S) ((*(S)->select.type->is_single)(S))
#define H5S_SELECT_IS_REGULAR(S) ((*(S)->select.type->is_regular)(S))
@ -175,6 +176,7 @@ typedef struct H5S_iostats_t {
#define H5S_SELECT_SERIAL_SIZE(S) (H5S_select_serial_size(S))
#define H5S_SELECT_SERIALIZE(S,BUF) (H5S_select_serialize(S,BUF))
#define H5S_SELECT_BOUNDS(S,START,END) (H5S_get_select_bounds(S,START,END))
#define H5S_SELECT_OFFSET(S, OFFSET) (H5S_get_select_offset(S, OFFSET))
#define H5S_SELECT_IS_CONTIGUOUS(S) (H5S_select_is_contiguous(S))
#define H5S_SELECT_IS_SINGLE(S) (H5S_select_is_single(S))
#define H5S_SELECT_IS_REGULAR(S) (H5S_select_is_regular(S))
@ -234,6 +236,7 @@ H5_DLL herr_t H5S_select_fill(const void *fill, size_t fill_size,
H5_DLL htri_t H5S_select_valid(const H5S_t *space);
H5_DLL hssize_t H5S_get_select_npoints(const H5S_t *space);
H5_DLL herr_t H5S_get_select_bounds(const H5S_t *space, hsize_t *start, hsize_t *end);
H5_DLL herr_t H5S_get_select_offset(const H5S_t *space, hsize_t *offset);
H5_DLL herr_t H5S_select_offset(H5S_t *space, const hssize_t *offset);
H5_DLL herr_t H5S_select_copy(H5S_t *dst, const H5S_t *src, hbool_t share_selection);
H5_DLL htri_t H5S_select_shape_same(const H5S_t *space1, const H5S_t *space2);

View File

@ -576,6 +576,46 @@ H5S_get_select_bounds(const H5S_t *space, hsize_t *start, hsize_t *end)
FUNC_LEAVE_NOAPI(ret_value);
} /* H5S_get_select_bounds() */
/*--------------------------------------------------------------------------
NAME
H5S_get_select_offset
PURPOSE
Gets the linear offset of the first element for the selection.
USAGE
herr_t H5S_get_select_offset(space, offset)
const H5S_t *space; IN: Dataspace pointer of selection to query
hsize_t *offset; OUT: Linear offset of first element in selection
RETURNS
Non-negative on success, negative on failure
DESCRIPTION
Retrieves the linear offset (in "units" of elements) of the first element
selected within the dataspace.
GLOBAL VARIABLES
COMMENTS, BUGS, ASSUMPTIONS
The offset calculation _does_ include the current offset of the
selection within the dataspace extent.
Calling this function on a "none" selection returns fail.
EXAMPLES
REVISION LOG
--------------------------------------------------------------------------*/
herr_t
H5S_get_select_offset(const H5S_t *space, hsize_t *offset)
{
herr_t ret_value; /* return value */
FUNC_ENTER_NOAPI_NOFUNC(H5S_get_select_offset)
/* Check args */
HDassert(space);
HDassert(offset);
ret_value = (*space->select.type->offset)(space, offset);
FUNC_LEAVE_NOAPI(ret_value)
} /* H5S_get_select_offset() */
/*--------------------------------------------------------------------------
NAME

View File

@ -6059,7 +6059,8 @@ test_random_chunks(void)
for(i = 0; i < NPOINTS; i++)
if(rbuf[i] != wbuf[i]){
printf(" Line %d: Incorrect value, wbuf[%u]=%d, rbuf[%u]=%d\n",__LINE__,(unsigned)i,wbuf[i],(unsigned)i,rbuf[i]);
TEST_ERROR;
printf(" coord[%u] = {%lu, %lu}\n", (unsigned)i, (unsigned long)coord[i][0], (unsigned long)coord[i][1]);
TEST_ERROR;
} /* end if */
/* Close resources */