summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorQuincey Koziol <koziol@hdfgroup.org>2007-07-03 17:16:32 (GMT)
committerQuincey Koziol <koziol@hdfgroup.org>2007-07-03 17:16:32 (GMT)
commit5164007d6d8e7348bd65f0fc55dd3190797f034f (patch)
treea0da189c291706562add7ae2b7f08ff397cd5037 /src
parentd7a3b8efcb5df94b0d0dad8fceec0f260f2b4230 (diff)
downloadhdf5-5164007d6d8e7348bd65f0fc55dd3190797f034f.zip
hdf5-5164007d6d8e7348bd65f0fc55dd3190797f034f.tar.gz
hdf5-5164007d6d8e7348bd65f0fc55dd3190797f034f.tar.bz2
[svn-r13933] Description:
Finish cleaning up "initialize by extent" routine (used when shrinking a dataset's dimensions) before addressing VL-datatype fill value bug. Tested on: Mac OS X/32 10.4.10 (amazon) Linux/32 2.6 (chicago) Linux/64 2.6 (chicago2)
Diffstat (limited to 'src')
-rw-r--r--src/H5Distore.c120
1 files changed, 61 insertions, 59 deletions
diff --git a/src/H5Distore.c b/src/H5Distore.c
index 56bf263..d2520cc 100644
--- a/src/H5Distore.c
+++ b/src/H5Distore.c
@@ -2943,7 +2943,7 @@ H5D_istore_allocate(H5D_t *dset, hid_t dxpl_id, hbool_t full_overwrite)
/* Increment indices */
carry = TRUE;
- for(i = (int)layout->u.chunk.ndims - 1; i >= 0; --i) {
+ for(i = (int)(space_ndims - 1); i >= 0; --i) {
chunk_offset[i] += layout->u.chunk.dim[i];
if(chunk_offset[i] >= space_dim[i])
chunk_offset[i] = 0;
@@ -3349,13 +3349,13 @@ H5D_istore_initialize_by_extent(H5D_io_info_t *io_info)
H5S_t *space_chunk = NULL; /* Dataspace for a chunk */
const H5O_layout_t *layout = &(io_info->dset->shared->layout); /* Dataset's layout */
H5D_storage_t store; /* Dataset storage information */
- hsize_t idx_cur[H5O_LAYOUT_NDIMS]; /* Multi-dimensional counters */
- hsize_t idx_max[H5O_LAYOUT_NDIMS];
- hsize_t start[H5O_LAYOUT_NDIMS]; /* Starting location of hyperslab */
+ hsize_t dset_dims[H5O_LAYOUT_NDIMS]; /* Current dataspace dimensions */
hsize_t chunk_dims[H5O_LAYOUT_NDIMS]; /* Current chunk dimensions */
- hsize_t curr_dims[H5O_LAYOUT_NDIMS]; /* Current dataspace dimensions */
- hsize_t chunks[H5O_LAYOUT_NDIMS]; /* Current number of chunks in each dimension */
+ hsize_t chunk_offset[H5O_LAYOUT_NDIMS]; /* Logical location of the chunks */
+ hsize_t hyper_start[H5O_LAYOUT_NDIMS]; /* Starting location of hyperslab */
+ hsize_t nchunks[H5O_LAYOUT_NDIMS]; /* Current number of chunks in each dimension */
hsize_t down_chunks[H5O_LAYOUT_NDIMS]; /* "down" size of number of elements in each dimension */
+ hsize_t bytes_per_chunk; /* Bytes in chunk */
int srank; /* # of chunk dimensions (signed) */
unsigned rank; /* # of chunk dimensions */
hbool_t carry; /* Flag to indicate that chunk increment carrys to higher dimension (sorta) */
@@ -3371,19 +3371,22 @@ H5D_istore_initialize_by_extent(H5D_io_info_t *io_info)
HDassert(H5F_addr_defined(layout->u.chunk.addr));
/* Go get the rank & dimensions */
- if((srank = H5S_get_simple_extent_dims(io_info->dset->shared->space, curr_dims, NULL)) < 0)
+ if((srank = H5S_get_simple_extent_dims(io_info->dset->shared->space, dset_dims, NULL)) < 0)
HGOTO_ERROR(H5E_DATASET, H5E_CANTGET, FAIL, "can't get dataset dimensions")
H5_ASSIGN_OVERFLOW(rank, srank, int, unsigned);
- /* Round up to the next integer # of chunks, to accomodate partial chunks */
- for(u = 0; u < rank; u++)
- chunks[u] = ((curr_dims[u] + layout->u.chunk.dim[u]) - 1) / layout->u.chunk.dim[u];
-
/* Set size of lowest chunk dimension (the dataset element size) */
- curr_dims[rank] = layout->u.chunk.dim[rank];
+ dset_dims[rank] = layout->u.chunk.dim[rank];
+
+ /* Compute the number of chunks in dataset & the # of bytes in a chunk */
+ /* (round up to the next integer # of chunks, to accomodate partial chunks) */
+ for(u = 0, bytes_per_chunk = layout->u.chunk.dim[rank]; u < rank; u++) {
+ nchunks[u] = ((dset_dims[u] - 1) / layout->u.chunk.dim[u]) + 1;
+ bytes_per_chunk *= layout->u.chunk.dim[u];
+ } /* end for */
/* Get the "down" sizes for each dimension */
- if(H5V_array_down(rank, chunks, down_chunks) < 0)
+ if(H5V_array_down(rank, nchunks, down_chunks) < 0)
HGOTO_ERROR(H5E_INTERNAL, H5E_BADVALUE, FAIL, "can't compute 'down' sizes")
/* Create a data space for a chunk & set the extent */
@@ -3392,72 +3395,44 @@ H5D_istore_initialize_by_extent(H5D_io_info_t *io_info)
if(NULL == (space_chunk = H5S_create_simple(rank, chunk_dims, NULL)))
HGOTO_ERROR(H5E_DATASPACE, H5E_CANTCREATE, FAIL, "can't create simple dataspace")
- /*
- * Set up multi-dimensional counters (idx_max, and idx_cur) and
- * loop through the chunks copying each chunk from the application to the
- * chunk cache.
- */
- for(u = 0; u < layout->u.chunk.ndims; u++) {
- idx_max[u] = (curr_dims[u] - 1) / layout->u.chunk.dim[u] + 1;
- idx_cur[u] = 0;
- } /* end for */
-
/* Point to local dataset storage info */
HDassert(io_info->store == NULL); /* Make certain we aren't blowing anything away */
io_info->store = &store;
- /* Reset start array */
- HDmemset(start, 0, sizeof(start));
+ /* Reset hyperslab start array */
+ HDmemset(hyper_start, 0, sizeof(hyper_start));
+
+ /* Initialize current chunk offset to the origin (0, 0, 0, ...) */
+ HDmemset(chunk_offset, 0, sizeof(chunk_offset));
/* Loop over all chunks */
carry = FALSE;
while(!carry) {
- hsize_t chunk_offset[H5O_LAYOUT_NDIMS]; /* Logical location of the chunks */
- hsize_t naccessed; /* Bytes accessed in chunk */
hbool_t found; /* Initialize this entry */
int i; /* Local index variable */
- /* The location and size of the chunk being accessed */
- for(u = 0, naccessed = 1; u < layout->u.chunk.ndims; u++) {
- hsize_t sub_size; /* Size of chunk accessed in a given dimension */
-
- chunk_offset[u] = idx_cur[u] * layout->u.chunk.dim[u];
- sub_size = MIN((idx_cur[u] + 1) * layout->u.chunk.dim[u], curr_dims[u])
- - chunk_offset[u];
- naccessed *= sub_size;
- } /* end for */
-
/*
* Figure out what chunks have to be initialized. These are the chunks where the dataspace
* extent boundary is within the chunk
*/
found = FALSE;
- for(u = 0; u < rank; u++) {
- if((chunk_offset[u] + layout->u.chunk.dim[u]) > curr_dims[u]) {
+ for(u = 0; u < rank; u++)
+ if((chunk_offset[u] + layout->u.chunk.dim[u]) > dset_dims[u]) {
found = TRUE;
break;
} /* end if */
- } /* end for */
if(found) {
const H5O_fill_t *fill = &io_info->dset->shared->dcpl_cache.fill; /* Fill value information */
hsize_t count[H5O_LAYOUT_NDIMS]; /* Element count of hyperslab */
uint8_t *chunk; /* The file chunk */
unsigned idx_hint; /* Which chunk we're dealing with */
+ hsize_t bytes_kept; /* Bytes kept in chunk */
+ hsize_t bytes_accessed; /* Bytes accessed in chunk */
- /* Calculate the index of this chunk */
- if(H5V_chunk_index(rank, chunk_offset, layout->u.chunk.dim, down_chunks, &store.chunk.index) < 0)
- HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "can't get chunk index")
-
- store.chunk.offset = chunk_offset;
- if(NULL == (chunk = H5D_istore_lock(io_info, NULL, FALSE, &idx_hint)))
- HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to read raw data chunk")
-
- if(H5S_select_all(space_chunk, TRUE) < 0)
- HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to select space")
-
+ /* Compute the # of elements to leave with existing value, in each dimension */
for(u = 0; u < rank; u++)
- count[u] = MIN((idx_cur[u] + 1) * layout->u.chunk.dim[u], curr_dims[u] - chunk_offset[u]);
+ count[u] = MIN((chunk_offset[u] + layout->u.chunk.dim[u]), dset_dims[u] - chunk_offset[u]);
#ifdef H5D_ISTORE_DEBUG
HDfputs("cache:initialize:offset:[", stdout);
@@ -3470,26 +3445,53 @@ H5D_istore_initialize_by_extent(H5D_io_info_t *io_info)
HDfputs("]\n", stdout);
#endif
- if(H5S_select_hyperslab(space_chunk, H5S_SELECT_NOTB, start, NULL, count, NULL) < 0)
+ /* Select all elements in chunk, to begin with */
+ if(H5S_select_all(space_chunk, TRUE) < 0)
+ HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to select space")
+
+ /* "Subtract out" the elements to keep */
+ if(H5S_select_hyperslab(space_chunk, H5S_SELECT_NOTB, hyper_start, NULL, count, NULL) < 0)
HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to select hyperslab")
+ /* Calculate the index of this chunk */
+ if(H5V_chunk_index(rank, chunk_offset, layout->u.chunk.dim, down_chunks, &store.chunk.index) < 0)
+ HGOTO_ERROR(H5E_DATASPACE, H5E_BADRANGE, FAIL, "can't get chunk index")
+
+ /* Lock the chunk into the cache, to get a pointer to the chunk buffer */
+ store.chunk.offset = chunk_offset;
+ if(NULL == (chunk = H5D_istore_lock(io_info, NULL, FALSE, &idx_hint)))
+ HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to read raw data chunk")
+
/* Fill the selection in the memory buffer */
/* Use the size of the elements in the chunk directly instead of */
/* relying on the fill.size, which might be set to 0 if there is */
/* no fill-value defined for the dataset -QAK */
- H5_CHECK_OVERFLOW(curr_dims[rank],hsize_t,size_t);
- if(H5S_select_fill(fill->buf, (size_t)curr_dims[rank], space_chunk, chunk) < 0)
+ H5_CHECK_OVERFLOW(dset_dims[rank], hsize_t, size_t);
+ if(H5S_select_fill(fill->buf, (size_t)dset_dims[rank], space_chunk, chunk) < 0)
HGOTO_ERROR(H5E_DATASET, H5E_CANTENCODE, FAIL, "filling selection failed")
- if(H5D_istore_unlock(io_info, TRUE, idx_hint, chunk, (size_t)naccessed) < 0)
+ /* The number of bytes in the chunk being accessed */
+ for(u = 0, bytes_kept = 1; u < layout->u.chunk.ndims; u++) {
+ hsize_t sub_size; /* Size of chunk accessed in a given dimension */
+
+ sub_size = MIN((chunk_offset[u] + layout->u.chunk.dim[u]), dset_dims[u])
+ - chunk_offset[u];
+ bytes_kept *= sub_size;
+ } /* end for */
+ bytes_accessed = bytes_per_chunk - bytes_kept;
+
+ /* Release lock on chunk */
+ H5_CHECK_OVERFLOW(bytes_accessed, hsize_t, size_t);
+ if(H5D_istore_unlock(io_info, TRUE, idx_hint, chunk, (size_t)bytes_accessed) < 0)
HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL, "unable to unlock raw data chunk")
} /* end if */
/* Increment indices */
carry = TRUE;
- for(i = (int)rank; i >= 0; --i) {
- if(++idx_cur[i] >= idx_max[i])
- idx_cur[i] = 0;
+ for(i = (int)(rank - 1); i >= 0; --i) {
+ chunk_offset[i] += layout->u.chunk.dim[i];
+ if(chunk_offset[i] >= dset_dims[i])
+ chunk_offset[i] = 0;
else {
carry = FALSE;
break;