From 374e5ae39b6f05469c1bcbdcaf0a473f1dde1385 Mon Sep 17 00:00:00 2001 From: Robb Matzke Date: Fri, 30 Jan 1998 18:32:28 -0500 Subject: [svn-r209] Changes since 19980130 ---------------------- ./INSTALL Added instructions for which C flags to set for debugging. ./src/H5C.c ./src/H5Cpublic.h H5Cset_chunk() takes const pointer. ./src/H5D.c ./src/H5Dprivate.h ./src/H5Dpublic.h Added H5Dextend() to extend the dimensions of a dataset. ./src/H5Osdspace.c ./src/H5P.c ./src/H5Pprivate.h ./src/H5Ppublic.h ./test/cmpd_dset.c ./test/dsets.c ./test/th5p.c Added the optional `maxdims' argument to H5Pcreate_simple() and defined constant H5P_UNLIMITED which can appear in the maxdims. Added `const' to arguments. Implemented H5Pcopy() Removed the unused file argument from H5P_modify. Added H5P_extend(). Removed the `flags' field from simple data types and we determine if the `max' or `perm' arrays are valid by looking at the pointer. Cleaned up the H5O_sdspace_debug output. ./src/H5T.c Fixed a printf format. ./MANIFEST ./test/Makefile.in ./test/extend.c [NEW] Added a test for multi-dimensional unlimited dimensions. --- INSTALL | 44 +++++++++-- MANIFEST | 1 + src/H5C.c | 2 +- src/H5Cpublic.h | 2 +- src/H5D.c | 95 ++++++++++++++++++++++- src/H5Dprivate.h | 3 +- src/H5Dpublic.h | 1 + src/H5Osdspace.c | 115 +++++++++++++++------------- src/H5P.c | 226 ++++++++++++++++++++++++++++++++++++++++--------------- src/H5Pprivate.h | 10 +-- src/H5Ppublic.h | 4 +- src/H5T.c | 2 +- test/Makefile.in | 12 ++- test/cmpd_dset.c | 6 +- test/dsets.c | 6 +- test/extend.c | 131 ++++++++++++++++++++++++++++++++ test/th5p.c | 4 +- 17 files changed, 522 insertions(+), 142 deletions(-) create mode 100644 test/extend.c diff --git a/INSTALL b/INSTALL index c4018ef..0645320 100644 --- a/INSTALL +++ b/INSTALL @@ -32,11 +32,12 @@ Step 2. Configure makefiles. $ ./configure - * By default libraries, programs, and documentation are installed - under /usr/local/lib, /usr/local/bin, and /usr/local/man. - However, if you want them in some other location you can specify - a prefix to use instead of /usr/local. For instance, to install - in /usr/lib, /usr/bin, and /usr/man one would say + * By default libraries, include files, programs, and documentation + are installed under /usr/local/lib, /usr/local/include, + /usr/local/bin, and /usr/local/man. However, if you want them + in some other location you can specify a prefix to use instead + of /usr/local. For instance, to install in /usr/lib, + /usr/include, /usr/bin, and /usr/man one would say $ ./configure --prefix=/usr @@ -56,6 +57,33 @@ Step 2. Configure makefiles. $ CC=gcc CPPFLAGS=-DNDEBUG CFLAGS="-Wall -O3" ./configure + * The HDF team recommends the following C flags for this prototype + release of the library. + + o Full warnings, usually `-fullwarn' or `-Wall' depending on + the compiler. With GCC you may optionally add: + -Wpointer-arith -Wwrite-strings -Wstrict-prototypes + -Wmissing-prototypes -Wmissing-declarations -Wnested-externs + + o Symbol table, usually with `-g' + + o Turn on debugging code in the various packages. Some + packages just produce extra output while others traverse + data structures looking for things that seem to be wrong. + + -DH5AC_DEBUG - cache debugging + -DH5B_DEBUG - B-link-tree debugging + -DH5F_DEBUG - File debugging + -DH5G_DEBUG - Group debugging + -UH5O_DEBUG - Open/Close debugging (produces lots of output) + -DH5T_DEBUG - Data type conversion statistics + + o The default low level driver can be chosen with + + -DH5F_LOW_DFLT=H5F_LOW_STDIO - Use libc stdio.h functions + -DH5F_LOW_DFLT=H5F_LOW_SEC2 - Use system calls directly + + the default is to use stdio functions. * You can see a list of other configuration options by saying @@ -70,7 +98,7 @@ Step 3. Compile library, tests, and programs. Note: If you supplied some other make command through the MAKE environment variable in the previous step then use that command - instead. + instead. The same applies below. Note: If you're re-building the library after changing some files and you're not using GNU make and gcc, then you should say @@ -90,9 +118,9 @@ Step 4. Run confidence tests. The command will fail if any test fails. - Note: some versions of make will report that `test is up to + Note: some old versions of make will report that `test is up to date'. If this happens then run `make _test' instead or run - `make test' from within the test directory. + `make test' from within the test directory. Step 5. Install public files. diff --git a/MANIFEST b/MANIFEST index fbf9552..2da890f 100644 --- a/MANIFEST +++ b/MANIFEST @@ -131,6 +131,7 @@ ./test/cmpd_dset.c ./test/dsets.c ./test/dtypes.c +./test/extend.c ./test/hyperslab.c ./test/istore.c ./test/testhdf5.c diff --git a/src/H5C.c b/src/H5C.c index 46dd841..dde8411 100644 --- a/src/H5C.c +++ b/src/H5C.c @@ -769,7 +769,7 @@ H5Cget_layout(hid_t tid) *------------------------------------------------------------------------- */ herr_t -H5Cset_chunk(hid_t tid, int ndims, size_t dim[]) +H5Cset_chunk(hid_t tid, int ndims, const size_t dim[]) { int i; H5D_create_t *tmpl = NULL; diff --git a/src/H5Cpublic.h b/src/H5Cpublic.h index e21b368..aca09d2 100644 --- a/src/H5Cpublic.h +++ b/src/H5Cpublic.h @@ -59,7 +59,7 @@ herr_t H5Cset_istore_k (hid_t tid, int ik); herr_t H5Cget_istore_k (hid_t tid, int *ik/*out*/); herr_t H5Cset_layout (hid_t tid, H5D_layout_t layout); H5D_layout_t H5Cget_layout (hid_t tid); -herr_t H5Cset_chunk (hid_t tid, int ndims, size_t dim[]); +herr_t H5Cset_chunk (hid_t tid, int ndims, const size_t dim[]); int H5Cget_chunk (hid_t tid, int max_ndims, size_t dim[]/*out*/); #ifdef __cplusplus diff --git a/src/H5D.c b/src/H5D.c index 5e31e3f..ef88f00 100644 --- a/src/H5D.c +++ b/src/H5D.c @@ -540,7 +540,50 @@ H5Dwrite(hid_t dataset_id, hid_t mem_type_id, hid_t mem_space_id, } FUNC_LEAVE(SUCCEED); } + +/*------------------------------------------------------------------------- + * Function: H5Dextend + * + * Purpose: This function makes sure that the dataset is at least of size + * SIZE. The dimensionality of SIZE is the same as the data + * space of the dataset being changed. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5Dextend (hid_t dataset_id, const size_t *size) +{ + H5D_t *dataset = NULL; + + FUNC_ENTER (H5Dextend, FAIL); + /* Check args */ + if (H5_DATASET!=H5A_group (dataset_id) || + NULL==(dataset=H5A_object (dataset_id))) { + HRETURN_ERROR (H5E_ARGS, H5E_BADTYPE, FAIL, "not a dataset"); + } + if (!size) { + HRETURN_ERROR (H5E_ARGS, H5E_BADVALUE, FAIL, "no size specified"); + } + + /* Increase size */ + if (H5D_extend (dataset, size)<0) { + HRETURN_ERROR (H5E_DATASET, H5E_CANTINIT, FAIL, + "unable to extend dataset"); + } + + FUNC_LEAVE (SUCCEED); +} + /*------------------------------------------------------------------------- * Function: H5D_find_name * @@ -627,7 +670,7 @@ H5D_create(H5F_t *f, const char *name, const H5T_t *type, const H5P_t *space, } /* Update the type and space header messages */ if (H5O_modify(&(new_dset->ent), H5O_DTYPE, 0, 0, new_dset->type) < 0 || - H5P_modify(f, &(new_dset->ent), new_dset->space) < 0) { + H5P_modify(&(new_dset->ent), new_dset->space) < 0) { HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, NULL, "can't update type or space header messages"); } @@ -1132,3 +1175,53 @@ H5D_write(H5D_t *dataset, const H5T_t *mem_type, const H5P_t *mem_space, bkg_buf = H5MM_xfree (bkg_buf); FUNC_LEAVE(ret_value); } + +/*------------------------------------------------------------------------- + * Function: H5D_extend + * + * Purpose: Increases the size of a dataset. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5D_extend (H5D_t *dataset, const size_t *size) +{ + herr_t changed; + + FUNC_ENTER (H5D_extend, FAIL); + + /* Check args */ + assert (dataset); + assert (size); + + /* This is only allowed for data spaces with chunked layout */ + if (H5D_CHUNKED!=dataset->layout.type) { + HRETURN_ERROR (H5E_DATASET, H5E_UNSUPPORTED, FAIL, + "size can only be increased for chunked datasets"); + } + + /* Increase the size of the data space */ + if ((changed=H5P_extend (dataset->space, size))<0) { + HRETURN_ERROR (H5E_DATASET, H5E_CANTINIT, FAIL, + "unable to increase size of data space"); + } + + /* Save the new dataspace in the file if necessary */ + if (changed>0 && + H5P_modify (&(dataset->ent), dataset->space)<0) { + HRETURN_ERROR (H5E_DATASET, H5E_WRITEERROR, FAIL, + "unable to update file with new dataspace"); + } + + FUNC_LEAVE (SUCCEED); +} + diff --git a/src/H5Dprivate.h b/src/H5Dprivate.h index f8a588f..840b462 100644 --- a/src/H5Dprivate.h +++ b/src/H5Dprivate.h @@ -58,7 +58,6 @@ herr_t H5D_write (H5D_t *dataset, const H5T_t *mem_type, const H5P_t *mem_space, const H5P_t *file_space, const H5D_xfer_t *xfer_parms, const void *buf); hid_t H5D_find_name (hid_t file_id, group_t UNUSED, const char *name); +herr_t H5D_extend (H5D_t *dataset, const size_t *size); -/* Functions defined in in H5Dconv.c */ -herr_t H5D_convert_buf (void *dst, const void *src, uintn len, uintn size); #endif diff --git a/src/H5Dpublic.h b/src/H5Dpublic.h index 00847b6..62a63d5 100644 --- a/src/H5Dpublic.h +++ b/src/H5Dpublic.h @@ -44,6 +44,7 @@ herr_t H5Dread (hid_t dataset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, hid_t xfer_parms_id, void *buf/*out*/); herr_t H5Dwrite (hid_t dataset_id, hid_t mem_type_id, hid_t mem_space_id, hid_t file_space_id, hid_t xfer_parms_id, const void *buf); +herr_t H5Dextend (hid_t dataset_id, const size_t *size); #ifdef __cplusplus } diff --git a/src/H5Osdspace.c b/src/H5Osdspace.c index 26330df..55c71a8 100644 --- a/src/H5Osdspace.c +++ b/src/H5Osdspace.c @@ -34,9 +34,7 @@ static herr_t H5O_sdspace_debug(H5F_t *f, const void *_mesg, FILE * stream, intn indent, intn fwidth); /* This message derives from H5O */ -const H5O_class_t H5O_SDSPACE[1] = -{ - { +const H5O_class_t H5O_SDSPACE[1] = {{ H5O_SDSPACE_ID, /* message id number */ "simple_dspace", /* message name for debugging */ sizeof(H5P_simple_t), /* native message size */ @@ -46,7 +44,7 @@ const H5O_class_t H5O_SDSPACE[1] = H5O_sdspace_size, /* size of symbol table entry */ NULL, /* default reset method */ H5O_sdspace_debug, /* debug the message */ - }}; +}}; /* Is the interface initialized? */ static hbool_t interface_initialize_g = FALSE; @@ -73,9 +71,10 @@ static hbool_t interface_initialize_g = FALSE; static void * H5O_sdspace_decode(H5F_t *f, size_t raw_size, const uint8 *p) { - H5P_simple_t *sdim = NULL; /* New simple dimensionality structure */ - uintn u; /* local counting variable */ - + H5P_simple_t *sdim = NULL; /* New simple dimensionality structure */ + uintn u; /* local counting variable */ + uintn flags; + FUNC_ENTER(H5O_sdspace_decode, NULL); /* check args */ @@ -86,17 +85,17 @@ H5O_sdspace_decode(H5F_t *f, size_t raw_size, const uint8 *p) /* decode */ if ((sdim = H5MM_xcalloc(1, sizeof(H5P_simple_t))) != NULL) { UINT32DECODE(p, sdim->rank); - UINT32DECODE(p, sdim->dim_flags); + UINT32DECODE(p, flags); if (sdim->rank > 0) { sdim->size = H5MM_xmalloc(sizeof(uint32) * sdim->rank); for (u = 0; u < sdim->rank; u++) UINT32DECODE(p, sdim->size[u]); - if (sdim->dim_flags & 0x01) { + if (flags & 0x01) { sdim->max = H5MM_xmalloc(sizeof(uint32) * sdim->rank); for (u = 0; u < sdim->rank; u++) UINT32DECODE(p, sdim->max[u]); } /* end if */ - if (sdim->dim_flags & 0x02) { + if (flags & 0x02) { sdim->perm = H5MM_xmalloc(sizeof(uint32) * sdim->rank); for (u = 0; u < sdim->rank; u++) UINT32DECODE(p, sdim->perm[u]); @@ -134,8 +133,9 @@ H5O_sdspace_decode(H5F_t *f, size_t raw_size, const uint8 *p) static herr_t H5O_sdspace_encode(H5F_t *f, size_t raw_size, uint8 *p, const void *mesg) { - const H5P_simple_t *sdim = (const H5P_simple_t *) mesg; - uintn u; /* Local counting variable */ + const H5P_simple_t *sdim = (const H5P_simple_t *) mesg; + uintn u; /* Local counting variable */ + uintn flags = 0; FUNC_ENTER(H5O_sdspace_encode, FAIL); @@ -145,17 +145,21 @@ H5O_sdspace_encode(H5F_t *f, size_t raw_size, uint8 *p, const void *mesg) assert(p); assert(sdim); + /* set flags */ + if (sdim->max) flags |= 0x01; + if (sdim->perm) flags |= 0x02; + /* encode */ UINT32ENCODE(p, sdim->rank); - UINT32ENCODE(p, sdim->dim_flags); + UINT32ENCODE(p, flags); if (sdim->rank > 0) { for (u = 0; u < sdim->rank; u++) UINT32ENCODE(p, sdim->size[u]); - if (sdim->dim_flags & 0x01) { + if (flags & 0x01) { for (u = 0; u < sdim->rank; u++) UINT32ENCODE(p, sdim->max[u]); } /* end if */ - if (sdim->dim_flags & 0x02) { + if (flags & 0x02) { for (u = 0; u < sdim->rank; u++) UINT32ENCODE(p, sdim->perm[u]); } /* end if */ @@ -193,24 +197,20 @@ H5O_sdspace_copy(const void *mesg, void *dest) /* deep copy -- pointed-to values are copied also */ HDmemcpy(dst, src, sizeof(H5P_simple_t)); - if (src->size) - dst->size = H5MM_xcalloc(src->rank, sizeof(uint32)); - if (src->max) - dst->max = H5MM_xcalloc(src->rank, sizeof(uint32)); - if (src->perm) - dst->perm = H5MM_xcalloc(src->rank, sizeof(uint32)); + + if (src->size) { + dst->size = H5MM_xcalloc(src->rank, sizeof(src->size[0])); + HDmemcpy (dst->size, src->size, src->rank*sizeof(src->size[0])); + } + if (src->max) { + dst->max = H5MM_xcalloc(src->rank, sizeof(src->max[0])); + HDmemcpy (dst->max, src->max, src->rank*sizeof(src->max[0])); + } + if (src->perm) { + dst->perm = H5MM_xcalloc(src->rank, sizeof(src->perm[0])); + HDmemcpy (dst->perm, src->perm, src->rank*sizeof(src->perm[0])); + } - if (src->rank > 0) { - HDmemcpy(dst->size, src->size, src->rank * sizeof(uint32)); - /* Check for maximum dimensions and copy those */ - if ((src->dim_flags & 0x01) > 0) { - HDmemcpy(dst->max, src->max, src->rank * sizeof(uint32)); - } /* end if */ - /* Check for dimension permutation and copy those */ - if ((src->dim_flags & 0x02) > 0) { - HDmemcpy(dst->perm, src->perm, src->rank * sizeof(uint32)); - } /* end if */ - } /* end if */ FUNC_LEAVE((void *) dst); } @@ -239,8 +239,8 @@ H5O_sdspace_size(H5F_t *f, const void *mesg) FUNC_ENTER(H5O_sim_dtype_size, FAIL); ret_value += sdim->rank * 4; /* add in the dimension sizes */ - ret_value += ((sdim->dim_flags & 0x01) > 0) * sdim->rank * 4; /* add in the space for the maximum dimensions, if they are present */ - ret_value += ((sdim->dim_flags & 0x02) > 0) * sdim->rank * 4; /* add in the space for the dimension permutations, if they are present */ + ret_value += sdim->max ? sdim->rank * 4 : 0; /* add in the space for the maximum dimensions, if they are present */ + ret_value += sdim->perm ? sdim->rank * 4 : 0; /* add in the space for the dimension permutations, if they are present */ FUNC_LEAVE(ret_value); } @@ -282,23 +282,36 @@ H5O_sdspace_debug(H5F_t *f, const void *mesg, FILE * stream, fprintf(stream, "%*s%-*s %lu\n", indent, "", fwidth, "Rank:", (unsigned long) (sdim->rank)); - fprintf(stream, "%*s%-*s %lx\n", indent, "", fwidth, - "Flags:", - (unsigned long) (sdim->dim_flags)); - for (u = 0; u < sdim->rank; u++) - fprintf(stream, "%*s%-*s %lx\n", indent, "", fwidth, - "Dim Size:", - (unsigned long) (sdim->size[u])); - if (sdim->dim_flags & 0x01) - for (u = 0; u < sdim->rank; u++) - fprintf(stream, "%*s%-*s %lx\n", indent, "", fwidth, - "Dim Max:", - (unsigned long) (sdim->max[u])); - if (sdim->dim_flags & 0x02) - for (u = 0; u < sdim->rank; u++) - fprintf(stream, "%*s%-*s %lx\n", indent, "", fwidth, - "Dim Perm:", - (unsigned long) (sdim->perm[u])); + + fprintf(stream, "%*s%-*s {", indent, "", fwidth, "Dim Size:"); + for (u = 0; u < sdim->rank; u++) { + fprintf (stream, "%s%lu", u?", ":"", (unsigned long)(sdim->size[u])); + } + fprintf (stream, "}\n"); + + fprintf(stream, "%*s%-*s ", indent, "", fwidth, "Dim Max:"); + if (sdim->max) { + fprintf (stream, "{"); + for (u = 0; u < sdim->rank; u++) { + if (H5P_UNLIMITED==sdim->max[u]) { + fprintf (stream, "%sINF", u?", ":""); + } else { + fprintf (stream, "%s%lu\n", u?", ":"", + (unsigned long) (sdim->max[u])); + } + } + fprintf (stream, "}\n"); + } else { + fprintf (stream, "CONSTANT\n"); + } + + if (sdim->perm) { + fprintf(stream, "%*s%-*s {", indent, "", fwidth, "Dim Perm:"); + for (u = 0; u < sdim->rank; u++) { + fprintf (stream, "%s%lu", u?", ":"", + (unsigned long) (sdim->perm[u])); + } + } FUNC_LEAVE(SUCCEED); } diff --git a/src/H5P.c b/src/H5P.c index fad7918..a9a1dd6 100644 --- a/src/H5P.c +++ b/src/H5P.c @@ -23,7 +23,6 @@ static char RcsId[] = "@(#)$Revision$"; #include /*object headers */ #include /* Data-space functions */ - /* Interface initialization */ #define PABLO_MASK H5P_mask #define INTERFACE_INIT H5P_init_interface @@ -86,7 +85,14 @@ H5P_term_interface(void) /*------------------------------------------------------------------------- * Function: H5Pcreate_simple * - * Purpose: Creates a new simple data space object and opens it for access. + * Purpose: Creates a new simple data space object and opens it for + * access. The DIMS argument is the size of the simple dataset + * and the MAXDIMS argument is the upper limit on the size of + * the dataset. MAXDIMS may be the null pointer in which case + * the upper limit is the same as DIMS. If an element of + * MAXDIMS is zero then the corresponding dimension is unlimited, + * otherwise no element of MAXDIMS should be smaller than the + * corresponding element of DIMS. * * Return: Success: The ID for the new simple data space object. * @@ -102,31 +108,55 @@ H5P_term_interface(void) *------------------------------------------------------------------------- */ hid_t -H5Pcreate_simple(int rank, size_t dims[]) +H5Pcreate_simple(int rank, const size_t *dims, const size_t *maxdims) { - H5P_t *ds = NULL; - hid_t ret_value = FAIL; + H5P_t *ds = NULL; + hid_t ret_value = FAIL; + int i; FUNC_ENTER(H5Pcreate, FAIL); + /* Check arguments */ + if (rank<0) { + HRETURN_ERROR (H5E_ARGS, H5E_BADVALUE, FAIL, + "dimensionality cannot be negative"); + } + if (!dims) { + HRETURN_ERROR (H5E_ARGS, H5E_BADVALUE, FAIL, + "no dimensions specified"); + } + if (maxdims) { + for (i=0; itype = H5P_SIMPLE; - ds->hslab_def=FALSE; /* no hyperslab defined currently */ + ds->hslab_def = FALSE; /* no hyperslab defined currently */ /* Initialize rank and dimensions */ ds->u.simple.rank = rank; - ds->u.simple.dim_flags = 0; /* max & perm information is not valid/useful */ + ds->u.simple.size = H5MM_xcalloc(1, rank*sizeof(size_t)); HDmemcpy(ds->u.simple.size, dims, rank*sizeof(size_t)); - ds->u.simple.max = H5MM_xcalloc(1, rank*sizeof(size_t)); - ds->u.simple.perm = H5MM_xcalloc(1, rank*sizeof(intn)); + if (maxdims) { + ds->u.simple.max = H5MM_xcalloc(1, rank*sizeof(size_t)); + HDmemcpy (ds->u.simple.max, maxdims, rank*sizeof(size_t)); + } + /* Register the new data space and get an ID for it */ if ((ret_value = H5A_register(H5_DATASPACE, ds)) < 0) { HGOTO_ERROR(H5E_ATOM, H5E_CANTREGISTER, FAIL, "unable to register data space for ID"); } - done: + + done: if (ret_value < 0) { H5MM_xfree(ds); } @@ -210,18 +240,64 @@ H5P_close(H5P_t *ds) assert("unknown data space type" && 0); break; } - if(ds->hslab_def==TRUE) - { + if(ds->hslab_def==TRUE) { H5MM_xfree(ds->h.start); H5MM_xfree(ds->h.count); H5MM_xfree(ds->h.stride); - } /* end if */ + } /* end if */ H5MM_xfree(ds); FUNC_LEAVE(SUCCEED); } /*------------------------------------------------------------------------- + * Function: H5Pcopy + * + * Purpose: Copies a dataspace. + * + * Return: Success: ID of the new dataspace + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +hid_t +H5Pcopy (hid_t space_id) +{ + H5P_t *src = NULL; + H5P_t *dst = NULL; + hid_t ret_value = FAIL; + + FUNC_ENTER (H5Pcopy, FAIL); + + /* Check args */ + if (H5_DATASPACE!=H5A_group (space_id) || + NULL==(src=H5A_object (space_id))) { + HRETURN_ERROR (H5E_ARGS, H5E_BADTYPE, FAIL, "not a data space"); + } + + /* Copy */ + if (NULL==(dst=H5P_copy (src))) { + HRETURN_ERROR (H5E_DATASPACE, H5E_CANTINIT, FAIL, + "unable to copy data space"); + } + + /* Atomize */ + if ((ret_value=H5A_register (H5_DATASPACE, dst))<0) { + HRETURN_ERROR (H5E_ATOM, H5E_CANTREGISTER, FAIL, + "unable to register data space atom"); + } + + FUNC_LEAVE (ret_value); +} + + +/*------------------------------------------------------------------------- * Function: H5P_copy * * Purpose: Copies a data space. @@ -579,11 +655,10 @@ H5P_get_dims(const H5P_t *ds, size_t dims[]) *------------------------------------------------------------------------- */ herr_t -H5P_modify(H5F_t *f, H5G_entry_t *ent, const H5P_t *ds) +H5P_modify(H5G_entry_t *ent, const H5P_t *ds) { - FUNC_ENTER(H5O_modify, FAIL); + FUNC_ENTER(H5P_modify, FAIL); - assert(f); assert(ent); assert(ds); @@ -692,8 +767,6 @@ H5P_cmp(const H5P_t *ds1, const H5P_t *ds2) if (ds1->u.simple.rank > ds2->u.simple.rank) HRETURN(1); - /* don't compare flags */ - for (i = 0; i < ds1->u.simple.rank; i++) { if (ds1->u.simple.size[i] < ds2->u.simple.size[i]) HRETURN(-1); @@ -713,8 +786,7 @@ H5P_cmp(const H5P_t *ds1, const H5P_t *ds2) } /* Check if we should compare hyperslab definitions */ - if(ds1->hslab_def==TRUE && ds2->hslab_def==TRUE) - { + if(ds1->hslab_def==TRUE && ds2->hslab_def==TRUE) { for (i = 0; i < ds1->u.simple.rank; i++) { if (ds1->h.start[i] < ds2->h.start[i]) HRETURN(-1); @@ -729,12 +801,10 @@ H5P_cmp(const H5P_t *ds1, const H5P_t *ds2) if (ds1->h.stride[i] > ds2->h.stride[i]) HRETURN(1); } - } /* end if */ - else - { + } else { if(ds1->hslab_def!=ds2->hslab_def) HRETURN(ds1->hslab_def==TRUE ? 1 : -1); - } /* end else */ + } break; @@ -842,11 +912,21 @@ H5Pset_space(hid_t sid, int rank, const size_t *dims) FUNC_ENTER(H5Pset_space, FAIL); - /* Get the object */ + /* Check args */ if ((space = H5A_object(sid)) == NULL) - HGOTO_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "not a data space"); + HRETURN_ERROR(H5E_ATOM, H5E_BADATOM, FAIL, "not a data space"); if (rank > 0 && dims == NULL) - HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "invalid rank"); + HRETURN_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no dimensions specified"); + if (rank<0) + HRETURN_ERROR (H5E_ARGS, H5E_BADVALUE, FAIL, "invalid rank"); + if (dims) { + for (u=0; utype) { @@ -863,37 +943,29 @@ H5Pset_space(hid_t sid, int rank, const size_t *dims) /* Fall through to report error */ default: - HGOTO_ERROR(H5E_DATASPACE, H5E_BADVALUE, FAIL, - "unknown data space class"); - } /* end switch */ + HRETURN_ERROR(H5E_DATASPACE, H5E_BADVALUE, FAIL, + "unknown data space class"); + } space->type = H5P_SIMPLE; /* Reset hyperslab definition, if one is defined */ - if(space->hslab_def==TRUE) - { + if(space->hslab_def==TRUE) { H5MM_xfree(space->h.start); H5MM_xfree(space->h.count); H5MM_xfree(space->h.stride); space->hslab_def=FALSE; - - } /* end if */ + } if (rank == 0) { /* scalar variable */ space->type = H5P_SCALAR; space->u.simple.rank = 0; /* set to scalar rank */ - space->u.simple.dim_flags = 0; /* no maximum dimensions or dimension permutations */ if (space->u.simple.size != NULL) space->u.simple.size = H5MM_xfree(space->u.simple.size); if (space->u.simple.max != NULL) space->u.simple.max = H5MM_xfree(space->u.simple.max); if (space->u.simple.perm != NULL) space->u.simple.max = H5MM_xfree(space->u.simple.perm); - } - /* end if */ - else { - /* Reset the dataspace flags */ - space->u.simple.dim_flags = 0; - + } else { /* Free the old space for now */ if (space->u.simple.size != NULL) space->u.simple.size = H5MM_xfree(space->u.simple.size); @@ -907,25 +979,7 @@ H5Pset_space(hid_t sid, int rank, const size_t *dims) space->u.simple.size = H5MM_xcalloc(rank, sizeof(size_t)); HDmemcpy(space->u.simple.size, dims, sizeof(size_t) * rank); - /* check if there are unlimited dimensions and create the maximum dims array */ - for (u = 0; u < rank; u++) - if (dims[u] == 0) { - if (u > 0) - HGOTO_ERROR(H5E_DATASPACE, H5E_UNSUPPORTED, FAIL, - "unlimited dimensions not in the lowest " - "dimensionality"); - space->u.simple.max = H5MM_xcalloc(rank, sizeof(size_t)); - HDmemcpy(space->u.simple.max, dims, sizeof(size_t) * rank); - space->u.simple.dim_flags |= H5P_VALID_MAX; - break; - } /* end if */ - } /* end else */ - - done: - if (ret_value == FAIL) { /* Error condition cleanup */ - - } /* end if */ - /* Normal function cleanup */ + } FUNC_LEAVE(ret_value); } @@ -1176,3 +1230,55 @@ H5P_find (const H5P_t *mem_space, const H5P_t *file_space) FUNC_LEAVE (conv); } + +/*------------------------------------------------------------------------- + * Function: H5P_extend + * + * Purpose: Extend the dimensions of a data space. + * + * Return: Success: Number of dimensions whose size increased. + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +intn +H5P_extend (H5P_t *space, const size_t *size) +{ + intn i, ret_value=0; + + FUNC_ENTER (H5P_extend, FAIL); + + /* Check args */ + assert (space && H5P_SIMPLE==space->type); + assert (size); + + for (i=0; iu.simple.rank; i++) { + if (space->u.simple.size[i]u.simple.max && + H5P_UNLIMITED!=space->u.simple.max[i] && + space->u.simple.max[i]u.simple.rank; i++) { + if (space->u.simple.size[i]u.simple.size[i] = size[i]; + } + } + } + + FUNC_LEAVE (ret_value); +} + diff --git a/src/H5Pprivate.h b/src/H5Pprivate.h index aa4c710..b64711e 100644 --- a/src/H5Pprivate.h +++ b/src/H5Pprivate.h @@ -37,13 +37,12 @@ typedef struct H5P_hyperslab_t { typedef struct H5P_simple_t { intn rank; /*number of dimensions */ - intn dim_flags; /*dimension flags */ size_t *size; /*dimension sizes */ - size_t *max; /*maximum dimension sizes */ - intn *perm; /*dimension permutations */ + size_t *max; /*maximum dimension sizes or NULL */ + intn *perm; /*dimension permutations or NULL */ } H5P_simple_t; -typedef struct { +typedef struct H5P_t { H5P_class_t type; /*type of dimensionality object */ union { H5P_simple_t simple; /*simple dimensionality information */ @@ -96,7 +95,7 @@ herr_t H5P_close (H5P_t *ds); size_t H5P_get_npoints (const H5P_t *ds); intn H5P_get_ndims (const H5P_t *ds); intn H5P_get_dims (const H5P_t *ds, size_t dims[]/*out*/); -herr_t H5P_modify (H5F_t *f, H5G_entry_t *ent, const H5P_t *space); +herr_t H5P_modify (H5G_entry_t *ent, const H5P_t *space); H5P_t *H5P_read (H5F_t *f, H5G_entry_t *ent); intn H5P_cmp (const H5P_t *ds1, const H5P_t *ds2); hbool_t H5P_is_simple (const H5P_t *sdim); @@ -104,6 +103,7 @@ uintn H5P_nelem (const H5P_t *space); const H5P_conv_t *H5P_find (const H5P_t *mem_space, const H5P_t *file_space); intn H5P_get_hyperslab (const H5P_t *ds, int offset[]/*out*/, size_t size[]/*out*/, size_t stride[]/*out*/); +intn H5P_extend (H5P_t *space, const size_t *size); /* Conversion functions for simple data spaces */ size_t H5P_simp_init (const struct H5O_layout_t *layout, diff --git a/src/H5Ppublic.h b/src/H5Ppublic.h index 26e70e6..72f3c55 100644 --- a/src/H5Ppublic.h +++ b/src/H5Ppublic.h @@ -22,6 +22,7 @@ /* Define atomic datatypes */ #define H5P_ALL (-2) +#define H5P_UNLIMITED 0 /* Different types of dataspaces */ typedef enum H5P_class_t { @@ -36,7 +37,8 @@ extern "C" { #endif /* Functions in H5P.c */ -hid_t H5Pcreate_simple (int rank, size_t dims[]); +hid_t H5Pcreate_simple (int rank, const size_t dims[], const size_t maxdims[]); +hid_t H5Pcopy (hid_t space_id); herr_t H5Pclose (hid_t space_id); size_t H5Pget_npoints (hid_t space_id); int H5Pget_ndims (hid_t space_id); diff --git a/src/H5T.c b/src/H5T.c index 8e52542..4506569 100644 --- a/src/H5T.c +++ b/src/H5T.c @@ -3239,7 +3239,7 @@ H5T_debug(H5T_t *dt, FILE * stream) break; } - fprintf(stream, "%s%s {nbytes=%ul", + fprintf(stream, "%s%s {nbytes=%lu", s, dt->locked ? "[!]" : "", (unsigned long)(dt->size)); if (H5T_is_atomic(dt)) { diff --git a/test/Makefile.in b/test/Makefile.in index a2259cd..76cc68d 100644 --- a/test/Makefile.in +++ b/test/Makefile.in @@ -11,11 +11,11 @@ CPPFLAGS=-I. -I../src @CPPFLAGS@ # These are our main targets. They should be listed in the order to be # executed, generally most specific tests to least specific tests. -PROGS=testhdf5 hyperslab istore dtypes dsets cmpd_dset +PROGS=testhdf5 hyperslab istore dtypes dsets cmpd_dset extend TESTS=$(PROGS) # Temporary files -MOSTLYCLEAN=cmpd_dset.h5 dataset.h5 istore.h5 tfile1.h5 tfile2.h5 \ +MOSTLYCLEAN=cmpd_dset.h5 dataset.h5 extend.h5 istore.h5 tfile1.h5 tfile2.h5 \ tfile3.h5 th5p1.h5 theap.h5 tohdr.h5 tstab1.h5 tstab2.h5 # Source and object files for programs... The PROG_SRC list contains all the @@ -23,7 +23,7 @@ MOSTLYCLEAN=cmpd_dset.h5 dataset.h5 istore.h5 tfile1.h5 tfile2.h5 \ # other source lists are for the individual tests, the files of which may # overlap with other tests. PROG_SRC=testhdf5.c tfile.c theap.c tmeta.c tohdr.c tstab.c th5p.c dtypes.c \ - hyperslab.c istore.c dsets.c cmpd_dset.c + hyperslab.c istore.c dsets.c cmpd_dset.c extend.c PROG_OBJ=$(PROG_SRC:.c=.o) TESTHDF5_SRC=testhdf5.c tfile.c theap.c tmeta.c tohdr.c tstab.c th5p.c @@ -44,6 +44,9 @@ ISTORE_OBJ=$(ISTORE_SRC:.c=.o) CMPD_DSET_SRC=cmpd_dset.c CMPD_DSET_OBJ=$(CMPD_DSET_SRC:.c=.o) +EXTEND_SRC=extend.c +EXTEND_OBJ=$(EXTEND_SRC:.c=.o) + # Private header files (not to be installed)... PRIVATE_HDR=testhdf5.h @@ -66,4 +69,7 @@ istore: $(ISTORE_OBJ) ../src/libhdf5.a cmpd_dset: $(CMPD_DSET_OBJ) ../src/libhdf5.a $(CC) $(CFLAGS) -o $@ $(CMPD_DSET_OBJ) ../src/libhdf5.a $(LIBS) +extend: $(EXTEND_OBJ) ../src/libhdf5.a + $(CC) $(CFLAGS) -o $@ $(EXTEND_OBJ) ../src/libhdf5.a $(LIBS) + @CONCLUDE@ diff --git a/test/cmpd_dset.c b/test/cmpd_dset.c index 489d8f4..c8afe38 100644 --- a/test/cmpd_dset.c +++ b/test/cmpd_dset.c @@ -134,7 +134,7 @@ main (void) assert (file>=0); /* Create the data space */ - space = H5Pcreate_simple (2, dim); + space = H5Pcreate_simple (2, dim, NULL); assert (space>=0); @@ -356,7 +356,7 @@ STEP 7: Reading original dataset with explicit data space.\n"); fflush (stdout); /* Create the data space */ - s7_sid = H5Pcreate_simple (2, dim); + s7_sid = H5Pcreate_simple (2, dim, NULL); assert (s7_sid>=0); /* Read the dataset */ @@ -395,7 +395,7 @@ STEP 8: Read middle third hyperslab into memory array.\n"); assert (status>=0); /* Create memory data space */ - s8_m_sid = H5Pcreate_simple (2, h_size); + s8_m_sid = H5Pcreate_simple (2, h_size, NULL); assert (s8_m_sid>=0); /* Read the dataset */ diff --git a/test/dsets.c b/test/dsets.c index 58bfc4c..783ace3 100644 --- a/test/dsets.c +++ b/test/dsets.c @@ -56,7 +56,7 @@ test_create(hid_t file) /* Create the data space */ dims[0] = 256; dims[1] = 512; - space = H5Pcreate_simple(2,dims); + space = H5Pcreate_simple(2, dims, NULL); assert(space != FAIL); /* @@ -208,7 +208,7 @@ test_simple_io(hid_t file) /* Create the data space */ dims[0] = 100; dims[1] = 200; - space = H5Pcreate_simple(2,dims); + space = H5Pcreate_simple(2, dims, NULL); assert(space != FAIL); /* Create the dataset */ @@ -296,7 +296,7 @@ test_tconv(hid_t file) /* Create the data space */ dims[0] = 1000000; - space = H5Pcreate_simple(1,dims); + space = H5Pcreate_simple (1, dims, NULL); assert(space != FAIL); /* Create the data set */ diff --git a/test/extend.c b/test/extend.c new file mode 100644 index 0000000..8cadd6a --- /dev/null +++ b/test/extend.c @@ -0,0 +1,131 @@ +/* + * Copyright (C) 1998 Spizella Software + * All rights reserved. + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Purpose: Tests extendable datasets. + */ +#include +#include + +#define NX 100 /* USE AN EVEN NUMBER!*/ +#define NY 100 /* USE AN EVEN NUMBER!*/ + + +/*------------------------------------------------------------------------- + * Function: main + * + * Purpose: Tests extendable datasets + * + * Return: Success: exit(0) + * + * Failure: exit(non-zero) + * + * Programmer: Robb Matzke + * Friday, January 30, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +int +main (void) +{ + hid_t file, dataset, mem_space, file_space, cparms; + herr_t status; + int i, j, k, m; + static int buf1[NY][NX], buf2[NX/2][NY/2]; + static const size_t dims[2] = {NX, NY}; + static const size_t half_dims[2] = {NX/2, NY/2}; + static size_t maxdims[2] = {H5P_UNLIMITED, H5P_UNLIMITED}; + static size_t size[2]; + int offset[2]; + + /* Initialize buffer and space */ + for (i=0; i=0); + + /* Create the file */ + file = H5Fcreate ("extend.h5", H5ACC_OVERWRITE, H5C_DEFAULT, H5C_DEFAULT); + assert (file>=0); + + /* Create the dataset which is originally NX by NY */ + cparms = H5Ccreate (H5C_DATASET_CREATE); + assert (cparms>=0); + status = H5Cset_chunk (cparms, 2, dims); + assert (status>=0); + dataset = H5Dcreate (file, "dataset", H5T_NATIVE_INT, mem_space, cparms); + assert (dataset>=0); + + /* Write the data */ + for (i=0; i<5; i++) { + for (j=0; j<5; j++) { + + /* Extend the dataset */ + offset[0] = i * NX; + offset[1] = j * NY; + size[0] = offset[0] + NX; + size[1] = offset[1] + NY; + status = H5Dextend (dataset, size); + assert (status>=0); + + /* Select a hyperslab */ + file_space = H5Dget_space (dataset); + assert (file_space>=0); + status = H5Pset_hyperslab (file_space, offset, dims, NULL); + assert (status>=0); + + /* Write to the hyperslab */ + status = H5Dwrite (dataset, H5T_NATIVE_INT, mem_space, file_space, + H5C_DEFAULT, buf1); + assert (status>=0); + H5Pclose (file_space); + } + } + H5Pclose (mem_space); + + + /* Read the data */ + mem_space = H5Pcreate_simple (2, half_dims, NULL); + for (i=0; i<10; i++) { + for (j=0; j<10; j++) { + + /* Select a hyperslab */ + offset[0] = i * NX/2; + offset[1] = j * NY/2; + file_space = H5Dget_space (dataset); + assert (file_space>=0); + status = H5Pset_hyperslab (file_space, offset, half_dims, NULL); + assert (status>=0); + + /* Read */ + status = H5Dread (dataset, H5T_NATIVE_INT, mem_space, file_space, + H5C_DEFAULT, buf2); + assert (status>=0); + H5Pclose (file_space); + + /* Compare */ + for (k=0; k