diff options
author | Quincey Koziol <koziol@hdfgroup.org> | 2007-07-24 19:10:00 (GMT) |
---|---|---|
committer | Quincey Koziol <koziol@hdfgroup.org> | 2007-07-24 19:10:00 (GMT) |
commit | 492e5ca2b48782bb4759ee1d0a59b0210f011528 (patch) | |
tree | f2c334cd5e2afb9ca40492340efe57d1f3af1ae6 /src | |
parent | 05973a4e8610a7f6893d0eaed9c3eee3b008ba60 (diff) | |
download | hdf5-492e5ca2b48782bb4759ee1d0a59b0210f011528.zip hdf5-492e5ca2b48782bb4759ee1d0a59b0210f011528.tar.gz hdf5-492e5ca2b48782bb4759ee1d0a59b0210f011528.tar.bz2 |
[svn-r14004] Description:
Fix problem with datatype messages where the version of the format
for a datatype message could depend on the "use the latest format" flag from
the file after it was initially created.
Tested on:
FreeBSD/32 6.2 (duty)
FreeBSD/64 6.2 (liberty)
Linux/32 2.6 (kagiso)
Mac OS X/32 10.4.10 (amazon)
Diffstat (limited to 'src')
-rw-r--r-- | src/H5A.c | 5 | ||||
-rw-r--r-- | src/H5D.c | 17 | ||||
-rw-r--r-- | src/H5Odtype.c | 101 | ||||
-rw-r--r-- | src/H5T.c | 484 | ||||
-rw-r--r-- | src/H5Tarray.c | 11 | ||||
-rw-r--r-- | src/H5Tcommit.c | 5 | ||||
-rw-r--r-- | src/H5Tcompound.c | 77 | ||||
-rw-r--r-- | src/H5Tdbg.c | 407 | ||||
-rw-r--r-- | src/H5Titerate.c | 155 | ||||
-rw-r--r-- | src/H5Tpkg.h | 79 | ||||
-rw-r--r-- | src/H5Tprivate.h | 1 | ||||
-rw-r--r-- | src/H5Tvlen.c | 21 | ||||
-rwxr-xr-x | src/Makefile.am | 8 | ||||
-rw-r--r-- | src/Makefile.in | 10 |
14 files changed, 889 insertions, 492 deletions
@@ -350,6 +350,11 @@ H5A_create(const H5G_loc_t *loc, const char *name, const H5T_t *type, if(H5T_set_loc(attr->dt, loc->oloc->file, H5T_LOC_DISK) < 0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location") + /* Set the latest format for datatype, if requested */ + if(H5F_USE_LATEST_FORMAT(loc->oloc->file)) + if(H5T_set_latest_version(attr->dt) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTSET, FAIL, "can't set latest version of datatype") + /* Copy the dataspace for the attribute */ attr->ds = H5S_copy(space, FALSE); @@ -1020,6 +1020,7 @@ H5D_init_type(H5F_t *file, const H5D_t *dset, hid_t type_id, const H5T_t *type) { htri_t relocatable; /* Flag whether the type is relocatable */ htri_t immutable; /* Flag whether the type is immutable */ + hbool_t use_latest_format; /* Flag indicating the newest file format should be used */ herr_t ret_value = SUCCEED; /* Return value */ FUNC_ENTER_NOAPI_NOINIT(H5D_init_type) @@ -1037,15 +1038,23 @@ H5D_init_type(H5F_t *file, const H5D_t *dset, hid_t type_id, const H5T_t *type) if((immutable = H5T_is_immutable(type)) < 0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "can't check datatype?") + /* Get the file's 'use the latest version of the format' flag */ + use_latest_format = H5F_USE_LATEST_FORMAT(file); + /* Copy the datatype if it's a custom datatype or if it'll change when it's location is changed */ - if(!immutable || relocatable) { + if(!immutable || relocatable || use_latest_format) { /* Copy datatype for dataset */ - if((dset->shared->type = H5T_copy(type, H5T_COPY_ALL))==NULL) - HGOTO_ERROR(H5E_DATATYPE, H5E_CANTCOPY, FAIL, "can't copy datatype") + if((dset->shared->type = H5T_copy(type, H5T_COPY_ALL)) == NULL) + HGOTO_ERROR(H5E_DATASET, H5E_CANTCOPY, FAIL, "can't copy datatype") /* Mark any datatypes as being on disk now */ if(H5T_set_loc(dset->shared->type, file, H5T_LOC_DISK) < 0) - HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid datatype location") + HGOTO_ERROR(H5E_DATASET, H5E_CANTINIT, FAIL, "can't set datatype location") + + /* Set the latest format, if requested */ + if(use_latest_format) + if(H5T_set_latest_version(dset->shared->type) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTSET, FAIL, "can't set latest version of datatype") /* Get a datatype ID for the dataset's datatype */ if((dset->shared->type_id = H5I_register(H5I_DATATYPE, dset->shared->type)) < 0) diff --git a/src/H5Odtype.c b/src/H5Odtype.c index 2bfaccf..1e97687 100644 --- a/src/H5Odtype.c +++ b/src/H5Odtype.c @@ -89,31 +89,6 @@ const H5O_msg_class_t H5O_MSG_DTYPE[1] = {{ H5O_dtype_shared_debug /* debug the message */ }}; -/* This is the version to create all datatypes which don't contain - * array datatypes (atomic types, compound datatypes without array fields, - * vlen sequences of objects which aren't arrays, etc.) or VAX byte-ordered - * objects. - */ -#define H5O_DTYPE_VERSION_1 1 - -/* This is the version to create all datatypes which contain H5T_ARRAY - * class objects (array definitely, potentially compound & vlen sequences also), - * but not VAX byte-ordered objects. - */ -#define H5O_DTYPE_VERSION_2 2 - -/* This is the version to create all datatypes which contain VAX byte-ordered - * objects (floating-point types, currently) (can also also H5T_ARRAY types - * also). - */ -/* This version also packs compound & enum field names without padding */ -/* This version also encodes the member offset of compound fields more efficiently */ -#define H5O_DTYPE_VERSION_3 3 - -/* The latest version of the format. Look through the 'encode helper' routine - * and 'size' callback for places to change when updating this. */ -#define H5O_DTYPE_VERSION_LATEST H5O_DTYPE_VERSION_3 - /*------------------------------------------------------------------------- * Function: H5O_dtype_decode_helper @@ -146,6 +121,7 @@ H5O_dtype_decode_helper(H5F_t *f, const uint8_t **pp, H5T_t *dt) version = (flags>>4) & 0x0f; if(version < H5O_DTYPE_VERSION_1 || version > H5O_DTYPE_VERSION_3) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTLOAD, FAIL, "bad version number for datatype message") + dt->shared->version = version; dt->shared->type = (H5T_class_t)(flags & 0x0f); flags >>= 8; @@ -515,6 +491,10 @@ done: * * Purpose: Encodes a datatype. * + * Note: When changing the format of a datatype (or adding a new one), + * remember to change the upgrade version callback + * (H5T_upgrade_version_cb). + * * Return: Non-negative on success/Negative on failure * * Programmer: Robb Matzke @@ -525,14 +505,10 @@ done: static herr_t H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) { - htri_t has_array = FALSE; /* Whether a compound datatype has an array inside it */ - hbool_t has_vax = FALSE; /* Whether VAX floating number exists */ unsigned flags = 0; char *hdr = (char *)*pp; unsigned i; size_t n, z; - uint8_t version; /* version number */ - hbool_t use_latest_format; /* Flag indicating the newest file format should be used */ herr_t ret_value = SUCCEED; /* Return value */ FUNC_ENTER_NOAPI_NOINIT(H5O_dtype_encode_helper) @@ -541,9 +517,6 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) HDassert(pp && *pp); HDassert(dt); - /* Get the file's 'use the latest version of the format' flag */ - use_latest_format = H5F_USE_LATEST_FORMAT(f); - /* skip the type and class bit-field for now */ *pp += 4; UINT32ENCODE(*pp, dt->shared->size); @@ -666,7 +639,7 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) break; case H5T_ORDER_VAX: /*turn on 1st and 6th (reserved before adding VAX) bits*/ flags |= 0x41; - has_vax = TRUE; + HDassert(dt->shared->version >= H5O_DTYPE_VERSION_3); break; default: HGOTO_ERROR(H5E_DATATYPE, H5E_UNSUPPORTED, FAIL, "byte order is not supported in file format yet") @@ -733,10 +706,6 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) { unsigned offset_nbytes; /* Size needed to encode member offsets */ - /* Check for an array datatype somewhere within the compound type */ - if((has_array = H5T_detect_class(dt, H5T_ARRAY)) < 0) - HGOTO_ERROR(H5E_DATATYPE, H5E_CANTENCODE, FAIL, "can't detect array class") - /* Compute the # of bytes required to store a member offset */ offset_nbytes = (H5V_log2_gen((uint64_t)dt->shared->size) + 7) / 8; @@ -745,12 +714,16 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) */ flags = dt->shared->u.compnd.nmembs & 0xffff; for(i = 0; i < dt->shared->u.compnd.nmembs; i++) { + /* Sanity check */ + /* (compound datatypes w/array members must be encoded w/version >= 2) */ + HDassert(dt->shared->u.compnd.memb[i].type->shared->type != H5T_ARRAY || dt->shared->version >= H5O_DTYPE_VERSION_2); + /* Name */ HDstrcpy((char*)(*pp), dt->shared->u.compnd.memb[i].name); /* Version 3 of the datatype message removed the padding to multiple of 8 bytes */ n = HDstrlen(dt->shared->u.compnd.memb[i].name); - if(use_latest_format) + if(dt->shared->version >= H5O_DTYPE_VERSION_3) *pp += n + 1; else { /* Pad name to multiple of 8 bytes */ @@ -761,7 +734,7 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) /* Member offset */ /* (starting with version 3 of the datatype message, use the minimum # of bytes required) */ - if(use_latest_format) + if(dt->shared->version >= H5O_DTYPE_VERSION_3) UINT32ENCODE_VAR(*pp, dt->shared->u.compnd.memb[i].offset, offset_nbytes) else UINT32ENCODE(*pp, dt->shared->u.compnd.memb[i].offset) @@ -770,7 +743,7 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) * member information, for better backward compatibility * Write out all zeros for the array information, though... */ - if(!has_array && !use_latest_format) { + if(dt->shared->version == H5O_DTYPE_VERSION_1) { unsigned j; /* Dimensionality */ @@ -810,13 +783,13 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTENCODE, FAIL, "unable to encode parent datatype") /* Names, each a multiple of eight bytes */ - for(i=0; i<dt->shared->u.enumer.nmembs; i++) { + for(i = 0; i < dt->shared->u.enumer.nmembs; i++) { /* Name */ HDstrcpy((char*)(*pp), dt->shared->u.enumer.name[i]); /* Version 3 of the datatype message removed the padding to multiple of 8 bytes */ n = HDstrlen(dt->shared->u.enumer.name[i]); - if(use_latest_format) + if(dt->shared->version >= H5O_DTYPE_VERSION_3) *pp += n + 1; else { /* Pad to multiple of 8 bytes */ @@ -882,7 +855,7 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) *(*pp)++ = dt->shared->u.array.ndims; /* Drop this information for Version 3 of the format */ - if(!use_latest_format) { + if(dt->shared->version < H5O_DTYPE_VERSION_3) { /* Reserved */ *(*pp)++ = '\0'; *(*pp)++ = '\0'; @@ -894,7 +867,7 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) UINT32ENCODE(*pp, dt->shared->u.array.dim[i]); /* Drop this information for Version 3 of the format */ - if(!use_latest_format) { + if(dt->shared->version < H5O_DTYPE_VERSION_3) { /* Encode 'fake' array dimension permutations */ for(i = 0; i < (unsigned)dt->shared->u.array.ndims; i++) UINT32ENCODE(*pp, i); @@ -910,21 +883,8 @@ H5O_dtype_encode_helper(const H5F_t *f, uint8_t **pp, const H5T_t *dt) break; } /* end switch */ - /* Set version #, based on actual features used for datatype */ - /* (unless the "use the latest format" flag is set, which can "upgrade" the - * format of certain encodings) - */ - if(use_latest_format) - version = H5O_DTYPE_VERSION_LATEST; - else if(has_vax) - version = H5O_DTYPE_VERSION_3; - else if(has_array) - version = H5O_DTYPE_VERSION_2; - else - version = H5O_DTYPE_VERSION_1; - /* Encode the type's class, version and bit field */ - *hdr++ = ((unsigned)(dt->shared->type) & 0x0f) | (version << 4); + *hdr++ = ((unsigned)(dt->shared->type) & 0x0f) | (dt->shared->version << 4); *hdr++ = (flags >> 0) & 0xff; *hdr++ = (flags >> 8) & 0xff; *hdr++ = (flags >> 16) & 0xff; @@ -1098,7 +1058,6 @@ static size_t H5O_dtype_size(const H5F_t *f, const void *_mesg) { const H5T_t *dt = (const H5T_t *)_mesg; - hbool_t use_latest_format; /* Flag indicating the newest file format should be used */ unsigned u; /* Local index variable */ size_t ret_value; @@ -1107,9 +1066,6 @@ H5O_dtype_size(const H5F_t *f, const void *_mesg) HDassert(f); HDassert(dt); - /* Get the file's 'use the latest version of the format' flag */ - use_latest_format = H5F_USE_LATEST_FORMAT(f); - /* Set the common size information */ ret_value = 4 + /* Type, class & flags */ 4; /* Size of datatype */ @@ -1134,13 +1090,8 @@ H5O_dtype_size(const H5F_t *f, const void *_mesg) case H5T_COMPOUND: { - htri_t has_array; /* Whether a compound datatype has an array inside it */ unsigned offset_nbytes; /* Size needed to encode member offsets */ - /* Check for an array datatype somewhere within the compound type */ - has_array = H5T_detect_class(dt, H5T_ARRAY); - HDassert(has_array >= 0); - /* Compute the # of bytes required to store a member offset */ offset_nbytes = (H5V_log2_gen((uint64_t)dt->shared->size) + 7) / 8; @@ -1151,17 +1102,17 @@ H5O_dtype_size(const H5F_t *f, const void *_mesg) /* Get length of field's name */ name_len = HDstrlen(dt->shared->u.compnd.memb[u].name); - /* Newer versions of the format don't pad out the name */ - if(use_latest_format) + /* Versions of the format >= 3 don't pad out the name */ + if(dt->shared->version >= H5O_DTYPE_VERSION_3) ret_value += name_len + 1; else ret_value += ((name_len + 8) / 8) * 8; /* Check for encoding array datatype or using the latest file format */ /* (starting with version 3 of the datatype message, use the minimum # of bytes required) */ - if(use_latest_format) + if(dt->shared->version >= H5O_DTYPE_VERSION_3) ret_value += offset_nbytes; /*member offset*/ - else if(has_array) + if(dt->shared->version >= H5O_DTYPE_VERSION_2) ret_value += 4; /*member offset*/ else ret_value += 4 + /*member offset*/ @@ -1183,8 +1134,8 @@ H5O_dtype_size(const H5F_t *f, const void *_mesg) /* Get length of field's name */ name_len = HDstrlen(dt->shared->u.enumer.name[u]); - /* Newer versions of the format don't pad out the name */ - if(use_latest_format) + /* Versions of the format >= 3 don't pad out the name */ + if(dt->shared->version >= H5O_DTYPE_VERSION_3) ret_value += name_len + 1; else ret_value += ((name_len + 8) / 8) * 8; @@ -1202,10 +1153,10 @@ H5O_dtype_size(const H5F_t *f, const void *_mesg) case H5T_ARRAY: ret_value += 1; /* ndims */ - if(!use_latest_format) + if(dt->shared->version < H5O_DTYPE_VERSION_3) ret_value += 3; /* reserved bytes*/ ret_value += 4 * dt->shared->u.array.ndims; /* dimensions */ - if(!use_latest_format) + if(dt->shared->version < H5O_DTYPE_VERSION_3) ret_value += 4 * dt->shared->u.array.ndims; /* dimension permutations */ ret_value += H5O_dtype_size(f, dt->shared->parent); break; @@ -260,7 +260,6 @@ H5FL_DEFINE(H5T_shared_t); H5FL_DEFINE(H5T_path_t); /* Static local functions */ -static herr_t H5T_print_stats(H5T_path_t *path, int *nprint/*in,out*/); static herr_t H5T_unregister(H5T_pers_t pers, const char *name, H5T_t *src, H5T_t *dst, H5T_conv_t func, hid_t dxpl_id); static herr_t H5T_register(H5T_pers_t pers, const char *name, H5T_t *src, @@ -287,38 +286,38 @@ static H5T_t *H5T_decode(const unsigned char *buf); /* Define the code template for bitfields for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_BITFIELD_CORE { \ - dt->shared->type = H5T_BITFIELD; \ + dt->shared->type = H5T_BITFIELD; \ } /* Define the code template for times for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_TIME_CORE { \ - dt->shared->type = H5T_TIME; \ + dt->shared->type = H5T_TIME; \ } /* Define the code template for types which reset the offset for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_OFFSET_CORE { \ - dt->shared->u.atomic.offset = 0; \ + dt->shared->u.atomic.offset = 0; \ } /* Define common code for all numeric types (floating-point & int, signed & unsigned) */ #define H5T_INIT_TYPE_NUM_COMMON(ENDIANNESS) { \ - dt->shared->u.atomic.order = ENDIANNESS; \ - dt->shared->u.atomic.offset = 0; \ - dt->shared->u.atomic.lsb_pad = H5T_PAD_ZERO; \ - dt->shared->u.atomic.msb_pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.order = ENDIANNESS; \ + dt->shared->u.atomic.offset = 0; \ + dt->shared->u.atomic.lsb_pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.msb_pad = H5T_PAD_ZERO; \ } /* Define the code templates for standard floats for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_FLOAT_COMMON(ENDIANNESS) { \ H5T_INIT_TYPE_NUM_COMMON(ENDIANNESS) \ - dt->shared->u.atomic.u.f.sign = 31; \ - dt->shared->u.atomic.u.f.epos = 23; \ - dt->shared->u.atomic.u.f.esize = 8; \ - dt->shared->u.atomic.u.f.ebias = 0x7f; \ - dt->shared->u.atomic.u.f.mpos = 0; \ - dt->shared->u.atomic.u.f.msize = 23; \ - dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ - dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.u.f.sign = 31; \ + dt->shared->u.atomic.u.f.epos = 23; \ + dt->shared->u.atomic.u.f.esize = 8; \ + dt->shared->u.atomic.u.f.ebias = 0x7f; \ + dt->shared->u.atomic.u.f.mpos = 0; \ + dt->shared->u.atomic.u.f.msize = 23; \ + dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ + dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ } #define H5T_INIT_TYPE_FLOATLE_CORE { \ @@ -332,14 +331,14 @@ static H5T_t *H5T_decode(const unsigned char *buf); /* Define the code templates for standard doubles for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_DOUBLE_COMMON(ENDIANNESS) { \ H5T_INIT_TYPE_NUM_COMMON(ENDIANNESS) \ - dt->shared->u.atomic.u.f.sign = 63; \ - dt->shared->u.atomic.u.f.epos = 52; \ - dt->shared->u.atomic.u.f.esize = 11; \ - dt->shared->u.atomic.u.f.ebias = 0x03ff; \ - dt->shared->u.atomic.u.f.mpos = 0; \ - dt->shared->u.atomic.u.f.msize = 52; \ - dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ - dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.u.f.sign = 63; \ + dt->shared->u.atomic.u.f.epos = 52; \ + dt->shared->u.atomic.u.f.esize = 11; \ + dt->shared->u.atomic.u.f.ebias = 0x03ff; \ + dt->shared->u.atomic.u.f.mpos = 0; \ + dt->shared->u.atomic.u.f.msize = 52; \ + dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ + dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ } #define H5T_INIT_TYPE_DOUBLELE_CORE { \ @@ -353,33 +352,35 @@ static H5T_t *H5T_decode(const unsigned char *buf); /* Define the code templates for VAX float for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_FLOATVAX_CORE { \ H5T_INIT_TYPE_NUM_COMMON(H5T_ORDER_VAX) \ - dt->shared->u.atomic.u.f.sign = 31; \ - dt->shared->u.atomic.u.f.epos = 23; \ - dt->shared->u.atomic.u.f.esize = 8; \ - dt->shared->u.atomic.u.f.ebias = 0x81; \ - dt->shared->u.atomic.u.f.mpos = 0; \ - dt->shared->u.atomic.u.f.msize = 23; \ - dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ - dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.u.f.sign = 31; \ + dt->shared->u.atomic.u.f.epos = 23; \ + dt->shared->u.atomic.u.f.esize = 8; \ + dt->shared->u.atomic.u.f.ebias = 0x81; \ + dt->shared->u.atomic.u.f.mpos = 0; \ + dt->shared->u.atomic.u.f.msize = 23; \ + dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ + dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->version = H5O_DTYPE_VERSION_3; \ } /* Define the code templates for VAX double for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_DOUBLEVAX_CORE { \ H5T_INIT_TYPE_NUM_COMMON(H5T_ORDER_VAX) \ - dt->shared->u.atomic.u.f.sign = 63; \ - dt->shared->u.atomic.u.f.epos = 52; \ - dt->shared->u.atomic.u.f.esize = 11; \ - dt->shared->u.atomic.u.f.ebias = 0x0401; \ - dt->shared->u.atomic.u.f.mpos = 0; \ - dt->shared->u.atomic.u.f.msize = 52; \ - dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ - dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->u.atomic.u.f.sign = 63; \ + dt->shared->u.atomic.u.f.epos = 52; \ + dt->shared->u.atomic.u.f.esize = 11; \ + dt->shared->u.atomic.u.f.ebias = 0x0401; \ + dt->shared->u.atomic.u.f.mpos = 0; \ + dt->shared->u.atomic.u.f.msize = 52; \ + dt->shared->u.atomic.u.f.norm = H5T_NORM_IMPLIED; \ + dt->shared->u.atomic.u.f.pad = H5T_PAD_ZERO; \ + dt->shared->version = H5O_DTYPE_VERSION_3; \ } /* Define the code templates for standard signed integers for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_SINT_COMMON(ENDIANNESS) { \ H5T_INIT_TYPE_NUM_COMMON(ENDIANNESS) \ - dt->shared->u.atomic.u.i.sign = H5T_SGN_2; \ + dt->shared->u.atomic.u.i.sign = H5T_SGN_2; \ } #define H5T_INIT_TYPE_SINTLE_CORE { \ @@ -407,30 +408,30 @@ static H5T_t *H5T_decode(const unsigned char *buf); /* Define a macro for common code for all newly allocate datatypes */ #define H5T_INIT_TYPE_ALLOC_COMMON(TYPE) { \ dt->sh_loc.type = H5O_SHARE_TYPE_UNSHARED; \ - dt->shared->type = TYPE; \ + dt->shared->type = TYPE; \ } /* Define the code templates for opaque for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_OPAQ_CORE { \ H5T_INIT_TYPE_ALLOC_COMMON(H5T_OPAQUE) \ - dt->shared->u.opaque.tag = H5MM_xstrdup(""); \ + dt->shared->u.opaque.tag = H5MM_xstrdup(""); \ } /* Define the code templates for strings for the "GUTS" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_STRING_COMMON { \ H5T_INIT_TYPE_ALLOC_COMMON(H5T_STRING) \ H5T_INIT_TYPE_NUM_COMMON(H5T_ORDER_NONE) \ - dt->shared->u.atomic.u.s.cset = H5F_DEFAULT_CSET; \ + dt->shared->u.atomic.u.s.cset = H5F_DEFAULT_CSET; \ } #define H5T_INIT_TYPE_CSTRING_CORE { \ H5T_INIT_TYPE_STRING_COMMON \ - dt->shared->u.atomic.u.s.pad = H5T_STR_NULLTERM; \ + dt->shared->u.atomic.u.s.pad = H5T_STR_NULLTERM; \ } #define H5T_INIT_TYPE_FORSTRING_CORE { \ H5T_INIT_TYPE_STRING_COMMON \ - dt->shared->u.atomic.u.s.pad = H5T_STR_SPACEPAD; \ + dt->shared->u.atomic.u.s.pad = H5T_STR_SPACEPAD; \ } /* Define the code templates for references for the "GUTS" in the H5T_INIT_TYPE macro */ @@ -441,20 +442,20 @@ static H5T_t *H5T_decode(const unsigned char *buf); #define H5T_INIT_TYPE_OBJREF_CORE { \ H5T_INIT_TYPE_REF_COMMON \ - dt->shared->force_conv = TRUE; \ - dt->shared->u.atomic.u.r.rtype = H5R_OBJECT; \ - dt->shared->u.atomic.u.r.loc = H5T_LOC_MEMORY; \ + dt->shared->force_conv = TRUE; \ + dt->shared->u.atomic.u.r.rtype = H5R_OBJECT; \ + dt->shared->u.atomic.u.r.loc = H5T_LOC_MEMORY; \ } #define H5T_INIT_TYPE_REGREF_CORE { \ H5T_INIT_TYPE_REF_COMMON \ - dt->shared->u.atomic.u.r.rtype = H5R_DATASET_REGION; \ + dt->shared->u.atomic.u.r.rtype = H5R_DATASET_REGION; \ } /* Define the code templates for the "SIZE_TMPL" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_SET_SIZE(SIZE) { \ - dt->shared->size = SIZE; \ - dt->shared->u.atomic.prec = 8*SIZE; \ + dt->shared->size = SIZE; \ + dt->shared->u.atomic.prec = 8 * SIZE; \ } #define H5T_INIT_TYPE_NOSET_SIZE(SIZE) { \ @@ -463,13 +464,13 @@ static H5T_t *H5T_decode(const unsigned char *buf); /* Define the code templates for the "CRT_TMPL" in the H5T_INIT_TYPE macro */ #define H5T_INIT_TYPE_COPY_CREATE(BASE) { \ /* Base off of existing datatype */ \ - if(NULL==(dt = H5T_copy(BASE,H5T_COPY_TRANSIENT))) \ + if(NULL == (dt = H5T_copy(BASE, H5T_COPY_TRANSIENT))) \ HGOTO_ERROR(H5E_RESOURCE, H5E_CANTCOPY, FAIL, "duplicating base type failed") \ } #define H5T_INIT_TYPE_ALLOC_CREATE(BASE) { \ /* Allocate new datatype info */ \ - if (NULL==(dt = H5T_alloc())) \ + if(NULL == (dt = H5T_alloc())) \ HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed") \ } @@ -479,14 +480,14 @@ static H5T_t *H5T_decode(const unsigned char *buf); H5_GLUE3(H5T_INIT_TYPE_,CRT_TMPL,_CREATE)(BASE) \ \ /* Adjust information for all types */ \ - dt->shared->state = H5T_STATE_IMMUTABLE; \ + dt->shared->state = H5T_STATE_IMMUTABLE; \ H5_GLUE3(H5T_INIT_TYPE_,SIZE_TMPL,_SIZE)(SIZE) \ \ /* Adjust information for this type */ \ H5_GLUE3(H5T_INIT_TYPE_,GUTS,_CORE) \ \ /* Atomize result */ \ - if ((GLOBAL = H5I_register(H5I_DATATYPE, dt)) < 0) \ + if((GLOBAL = H5I_register(H5I_DATATYPE, dt)) < 0) \ HGOTO_ERROR(H5E_DATATYPE, H5E_CANTREGISTER, FAIL, "unable to register datatype atom") \ } @@ -3277,7 +3278,7 @@ H5T_copy(const H5T_t *old_dt, H5T_copy_t method) /* Copy shared location information if the new type is named or if it is * shared in the heap. */ - if(old_dt->sh_loc.type == H5O_SHARE_TYPE_SOHM || + if((old_dt->sh_loc.type == H5O_SHARE_TYPE_SOHM || old_dt->sh_loc.type == H5O_SHARE_TYPE_HERE) || new_dt->shared->state == H5T_STATE_NAMED || new_dt->shared->state == H5T_STATE_OPEN) { if(H5O_set_shared(&(new_dt->sh_loc), &(old_dt->sh_loc)) < 0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTCOPY, NULL, "can't copy shared information") @@ -3357,8 +3358,6 @@ done: * Programmer: Quincey Koziol * Monday, August 29, 2005 * - * Modifications: - * *------------------------------------------------------------------------- */ H5T_t * @@ -3369,23 +3368,25 @@ H5T_alloc(void) FUNC_ENTER_NOAPI(H5T_alloc, NULL) - /* Allocate & initialize new datatype info */ + /* Allocate & initialize datatype wrapper info */ if(NULL == (dt = H5FL_CALLOC(H5T_t))) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "memory allocation failed") H5O_loc_reset(&(dt->oloc)); H5G_name_reset(&(dt->path)); H5O_msg_reset_share(H5O_DTYPE_ID, dt); + /* Allocate & initialize shared datatype structure */ if(NULL == (dt->shared = H5FL_CALLOC(H5T_shared_t))) HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, NULL, "memory allocation failed") + dt->shared->version = H5O_DTYPE_VERSION_1; /* Assign return value */ ret_value = dt; done: if(ret_value == NULL) - if(dt != NULL) { - if(dt->shared != NULL) + if(dt) { + if(dt->shared) H5FL_FREE(H5T_shared_t, dt->shared); H5FL_FREE(H5T_t, dt); } /* end if */ @@ -5071,8 +5072,6 @@ done: * Programmer: Quincey Koziol * Thursday, June 24, 2004 * - * Modifications: - * *------------------------------------------------------------------------- */ htri_t @@ -5080,323 +5079,124 @@ H5T_is_relocatable(const H5T_t *dt) { htri_t ret_value = FALSE; - FUNC_ENTER_NOAPI(H5T_is_relocatable, FAIL); + FUNC_ENTER_NOAPI(H5T_is_relocatable, FAIL) - assert(dt); + /* Sanity check */ + HDassert(dt); - if(H5T_detect_class(dt, H5T_VLEN)) - ret_value = TRUE; - else if(H5T_detect_class(dt, H5T_REFERENCE)) + /* VL and reference datatypes are relocatable */ + if(H5T_detect_class(dt, H5T_VLEN) || H5T_detect_class(dt, H5T_REFERENCE)) ret_value = TRUE; done: - FUNC_LEAVE_NOAPI(ret_value); + FUNC_LEAVE_NOAPI(ret_value) } /* end H5T_is_relocatable() */ - /*------------------------------------------------------------------------- - * Function: H5T_print_stats - * - * Purpose: Print statistics about a conversion path. Statistics are - * printed only if all the following conditions are true: + * Function: H5T_upgrade_version_cb * - * 1. The library was compiled with H5T_DEBUG defined. - * 2. Data type debugging is turned on at run time. - * 3. The path was called at least one time. + * Purpose: H5T_visit callback to Upgrade the version of a datatype + * (if there's any benefit to doing so) * - * The optional NPRINT argument keeps track of the number of - * conversions paths for which statistics have been shown. If - * its value is zero then table headers are printed before the - * first line of output. + * Note: The behavior below is tightly coupled with the "better" + * encodings for datatype messages in the datatype message + * encoding routine. * - * Return: Success: non-negative - * - * Failure: negative - * - * Programmer: Robb Matzke - * Monday, December 14, 1998 + * Return: Non-negative on success/Negative on failure * - * Modifications: + * Programmer: Quincey Koziol + * Thursday, July 19, 2007 * *------------------------------------------------------------------------- */ static herr_t -H5T_print_stats(H5T_path_t UNUSED * path, int UNUSED * nprint/*in,out*/) +H5T_upgrade_version_cb(H5T_t *dt, void *op_value) { -#ifdef H5T_DEBUG - hsize_t nbytes; - char bandwidth[32]; -#endif + FUNC_ENTER_NOAPI_NOINIT_NOFUNC(H5T_upgrade_version_cb) - FUNC_ENTER_NOAPI_NOINIT_NOFUNC(H5T_print_stats); + /* Sanity check */ + HDassert(dt); + HDassert(op_value); -#ifdef H5T_DEBUG - if (H5DEBUG(T) && path->stats.ncalls>0) { - if (nprint && 0==(*nprint)++) { - HDfprintf (H5DEBUG(T), "H5T: type conversion statistics:\n"); - HDfprintf (H5DEBUG(T), " %-16s %10s %10s %8s %8s %8s %10s\n", - "Conversion", "Elmts", "Calls", "User", - "System", "Elapsed", "Bandwidth"); - HDfprintf (H5DEBUG(T), " %-16s %10s %10s %8s %8s %8s %10s\n", - "----------", "-----", "-----", "----", - "------", "-------", "---------"); - } - if(path->src && path->dst) - nbytes = MAX (H5T_get_size (path->src), - H5T_get_size (path->dst)); - else if(path->src) - nbytes = H5T_get_size (path->src); - else if(path->dst) - nbytes = H5T_get_size (path->dst); - else - nbytes = 0; - nbytes *= path->stats.nelmts; - H5_bandwidth(bandwidth, (double)nbytes, - path->stats.timer.etime); - HDfprintf (H5DEBUG(T), " %-16s %10Hd %10d %8.2f %8.2f %8.2f %10s\n", - path->name, - path->stats.nelmts, - path->stats.ncalls, - path->stats.timer.utime, - path->stats.timer.stime, - path->stats.timer.etime, - bandwidth); - } -#endif - FUNC_LEAVE_NOAPI(SUCCEED); -} + /* Special behavior for each type of datatype */ + switch(dt->shared->type) { + case H5T_COMPOUND: + case H5T_ARRAY: + case H5T_ENUM: + /* These types benefit from "upgrading" their version */ + if(*(unsigned *)op_value > dt->shared->version) + dt->shared->version = *(unsigned *)op_value; + break; + + default: + break; + } /* end switch */ + FUNC_LEAVE_NOAPI(SUCCEED) +} /* end H5T_upgrade_version_cb() */ + + /*------------------------------------------------------------------------- - * Function: H5T_debug + * Function: H5T_upgrade_version * - * Purpose: Prints information about a data type. + * Purpose: Upgrade the version of a datatype (if there's any benefit to + * doing so) and recursively apply to compound members and/or + * parent datatypes. * * Return: Non-negative on success/Negative on failure * - * Programmer: Robb Matzke - * Wednesday, January 7, 1998 - * - * Modifications: + * Programmer: Quincey Koziol + * Thursday, July 19, 2007 * *------------------------------------------------------------------------- */ herr_t -H5T_debug(const H5T_t *dt, FILE *stream) +H5T_upgrade_version(H5T_t *dt, unsigned new_version) { - const char *s1="", *s2=""; - unsigned i; - size_t k, base_size; - uint64_t tmp; - herr_t ret_value=SUCCEED; /* Return value */ - - FUNC_ENTER_NOAPI(H5T_debug, FAIL); - - /* Check args */ - assert(dt); - assert(stream); - - switch (dt->shared->type) { - case H5T_INTEGER: - s1 = "int"; - break; - case H5T_FLOAT: - s1 = "float"; - break; - case H5T_TIME: - s1 = "time"; - break; - case H5T_STRING: - s1 = "str"; - break; - case H5T_BITFIELD: - s1 = "bits"; - break; - case H5T_OPAQUE: - s1 = "opaque"; - break; - case H5T_COMPOUND: - s1 = "struct"; - break; - case H5T_ENUM: - s1 = "enum"; - break; - case H5T_VLEN: - if(H5T_IS_VL_STRING(dt->shared)) - s1 = "str"; - else - s1 = "vlen"; - break; - default: - s1 = ""; - break; - } - - switch (dt->shared->state) { - case H5T_STATE_TRANSIENT: - s2 = "[transient]"; - break; - case H5T_STATE_RDONLY: - s2 = "[constant]"; - break; - case H5T_STATE_IMMUTABLE: - s2 = "[predefined]"; - break; - case H5T_STATE_NAMED: - s2 = "[named,closed]"; - break; - case H5T_STATE_OPEN: - s2 = "[named,open]"; - break; - } - - fprintf(stream, "%s%s {nbytes=%lu", s1, s2, (unsigned long)(dt->shared->size)); - - if (H5T_IS_ATOMIC(dt->shared)) { - switch (dt->shared->u.atomic.order) { - case H5T_ORDER_BE: - s1 = "BE"; - break; - case H5T_ORDER_LE: - s1 = "LE"; - break; - case H5T_ORDER_VAX: - s1 = "VAX"; - break; - case H5T_ORDER_NONE: - s1 = "NONE"; - break; - default: - s1 = "order?"; - break; - } - fprintf(stream, ", %s", s1); - - if (dt->shared->u.atomic.offset) { - fprintf(stream, ", offset=%lu", - (unsigned long) (dt->shared->u.atomic.offset)); - } - if (dt->shared->u.atomic.prec != 8 * dt->shared->size) { - fprintf(stream, ", prec=%lu", - (unsigned long) (dt->shared->u.atomic.prec)); - } - switch (dt->shared->type) { - case H5T_INTEGER: - switch (dt->shared->u.atomic.u.i.sign) { - case H5T_SGN_NONE: - s1 = "unsigned"; - break; - case H5T_SGN_2: - s1 = NULL; - break; - default: - s1 = "sign?"; - break; - } - if (s1) fprintf(stream, ", %s", s1); - break; - - case H5T_FLOAT: - switch (dt->shared->u.atomic.u.f.norm) { - case H5T_NORM_IMPLIED: - s1 = "implied"; - break; - case H5T_NORM_MSBSET: - s1 = "msbset"; - break; - case H5T_NORM_NONE: - s1 = "no-norm"; - break; - default: - s1 = "norm?"; - break; - } - fprintf(stream, ", sign=%lu+1", - (unsigned long) (dt->shared->u.atomic.u.f.sign)); - fprintf(stream, ", mant=%lu+%lu (%s)", - (unsigned long) (dt->shared->u.atomic.u.f.mpos), - (unsigned long) (dt->shared->u.atomic.u.f.msize), s1); - fprintf(stream, ", exp=%lu+%lu", - (unsigned long) (dt->shared->u.atomic.u.f.epos), - (unsigned long) (dt->shared->u.atomic.u.f.esize)); - tmp = dt->shared->u.atomic.u.f.ebias >> 32; - if (tmp) { - size_t hi=(size_t)tmp; - size_t lo =(size_t)(dt->shared->u.atomic.u.f.ebias & 0xffffffff); - fprintf(stream, " bias=0x%08lx%08lx", - (unsigned long)hi, (unsigned long)lo); - } else { - size_t lo = (size_t)(dt->shared->u.atomic.u.f.ebias & 0xffffffff); - fprintf(stream, " bias=0x%08lx", (unsigned long)lo); - } - break; + herr_t ret_value = SUCCEED; /* Return value */ - default: - /* No additional info */ - break; - } + FUNC_ENTER_NOAPI(H5T_upgrade_version, FAIL) - } else if (H5T_COMPOUND==dt->shared->type) { - /* Compound data type */ - for (i=0; i<dt->shared->u.compnd.nmembs; i++) { - fprintf(stream, "\n\"%s\" @%lu", - dt->shared->u.compnd.memb[i].name, - (unsigned long) (dt->shared->u.compnd.memb[i].offset)); - fprintf(stream, " "); - H5T_debug(dt->shared->u.compnd.memb[i].type, stream); - } - fprintf(stream, "\n"); + /* Sanity check */ + HDassert(dt); - } else if (H5T_VLEN==dt->shared->type) { - switch(dt->shared->u.vlen.loc) { - case H5T_LOC_MEMORY: - fprintf(stream, ", loc=memory"); - break; + /* Iterate over entire datatype, upgrading the version of components, if it's useful */ + if(H5T_visit(dt, (H5T_VISIT_SIMPLE | H5T_VISIT_COMPLEX_LAST), H5T_upgrade_version_cb, &new_version) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "iteration to upgrade datatype encoding version failed") - case H5T_LOC_DISK: - fprintf(stream, ", loc=disk"); - break; +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5T_upgrade_version() */ - default: - fprintf(stream, ", loc=UNKNOWN"); - break; - } /* end switch */ + +/*------------------------------------------------------------------------- + * Function: H5T_set_latest_version + * + * Purpose: Set the encoding for a datatype to the latest version. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Quincey Koziol + * Thursday, July 19, 2007 + * + *------------------------------------------------------------------------- + */ +herr_t +H5T_set_latest_version(H5T_t *dt) +{ + herr_t ret_value = SUCCEED; /* Return value */ - if(H5T_IS_VL_STRING(dt->shared)) { - /* Variable length string datatype */ - fprintf(stream, ", variable-length"); - } /* end if */ - else { - /* Variable length sequence datatype */ - fprintf(stream, " VLEN "); - H5T_debug(dt->shared->parent, stream); - fprintf(stream, "\n"); - } /* end else */ - - } else if (H5T_ENUM==dt->shared->type) { - /* Enumeration data type */ - fprintf(stream, " "); - H5T_debug(dt->shared->parent, stream); - base_size = dt->shared->parent->shared->size; - for (i=0; i<dt->shared->u.enumer.nmembs; i++) { - fprintf(stream, "\n\"%s\" = 0x", dt->shared->u.enumer.name[i]); - for (k=0; k<base_size; k++) { - fprintf(stream, "%02lx", - (unsigned long)(dt->shared->u.enumer.value+i*base_size+k)); - } - } - fprintf(stream, "\n"); + FUNC_ENTER_NOAPI(H5T_set_latest_version, FAIL) - } else if (H5T_OPAQUE==dt->shared->type) { - fprintf(stream, ", tag=\"%s\"", dt->shared->u.opaque.tag); + /* Sanity check */ + HDassert(dt); - } else { - /* Unknown */ - fprintf(stream, "unknown class %d\n", (int)(dt->shared->type)); - } - fprintf(stream, "}"); + /* Upgrade the format version for the datatype to the latest */ + if(H5T_upgrade_version(dt, H5O_DTYPE_VERSION_LATEST) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_CANTSET, FAIL, "can't upgrade datatype encoding") done: - FUNC_LEAVE_NOAPI(ret_value); -} + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5T_set_latest_version() */ diff --git a/src/H5Tarray.c b/src/H5Tarray.c index 05b8dc4..cef8f66 100644 --- a/src/H5Tarray.c +++ b/src/H5Tarray.c @@ -158,12 +158,13 @@ H5T_array_create(H5T_t *base, unsigned ndims, const hsize_t dim[/* ndims */]) /* Set the array's size (number of elements * element datatype's size) */ ret_value->shared->size = ret_value->shared->parent->shared->size * ret_value->shared->u.array.nelem; - /* - * Set the "force conversion" flag if the base datatype indicates - */ + /* Set the "force conversion" flag if the base datatype indicates */ if(base->shared->force_conv == TRUE) ret_value->shared->force_conv = TRUE; + /* Array datatypes need a later version of the datatype object header message */ + ret_value->shared->version = MAX(base->shared->version, H5O_DTYPE_VERSION_2); + done: FUNC_LEAVE_NOAPI(ret_value) } /* end H5T_array_create */ @@ -220,7 +221,7 @@ done: *------------------------------------------------------------------------- */ int -H5T_get_array_ndims(H5T_t *dt) +H5T_get_array_ndims(const H5T_t *dt) { FUNC_ENTER_NOAPI_NOINIT_NOFUNC(H5T_get_array_ndims) @@ -283,7 +284,7 @@ done: *------------------------------------------------------------------------- */ int -H5T_get_array_dims(H5T_t *dt, hsize_t dims[]) +H5T_get_array_dims(const H5T_t *dt, hsize_t dims[]) { unsigned u; /* Local index variable */ int ret_value; /* return value */ diff --git a/src/H5Tcommit.c b/src/H5Tcommit.c index 4c5d802..dba5524 100644 --- a/src/H5Tcommit.c +++ b/src/H5Tcommit.c @@ -314,6 +314,11 @@ H5T_commit(H5F_t *file, H5T_t *type, hid_t tcpl_id, hid_t dxpl_id) HGOTO_ERROR(H5E_SYM, H5E_CANTRESET, FAIL, "unable to initialize path") loc_init = TRUE; + /* Set the latest format, if requested */ + if(H5F_USE_LATEST_FORMAT(file)) + if(H5T_set_latest_version(type) < 0) + HGOTO_ERROR(H5E_DATASET, H5E_CANTSET, FAIL, "can't set latest version of datatype") + /* Calculate message size infomation, for creating object header */ dtype_size = H5O_msg_size_f(file, tcpl_id, H5O_DTYPE_ID, type, (size_t)0); HDassert(dtype_size); diff --git a/src/H5Tcompound.c b/src/H5Tcompound.c index fbaacfc..660a76d 100644 --- a/src/H5Tcompound.c +++ b/src/H5Tcompound.c @@ -30,9 +30,6 @@ #include "H5MMprivate.h" /*memory management */ #include "H5Tpkg.h" /*data-type functions */ -/* Local macros */ -#define H5T_COMPND_INC 64 /*typical max numb of members per struct */ - /* Static local functions */ static herr_t H5T_pack(const H5T_t *dt); @@ -416,59 +413,56 @@ done: *------------------------------------------------------------------------- */ herr_t -H5T_insert(const H5T_t *parent, const char *name, size_t offset, const H5T_t *member) +H5T_insert(H5T_t *parent, const char *name, size_t offset, const H5T_t *member) { unsigned idx, i; size_t total_size; - herr_t ret_value=SUCCEED; /* Return value */ + herr_t ret_value = SUCCEED; /* Return value */ FUNC_ENTER_NOAPI(H5T_insert, FAIL) /* check args */ - assert(parent && H5T_COMPOUND == parent->shared->type); - assert(H5T_STATE_TRANSIENT==parent->shared->state); - assert(member); - assert(name && *name); + HDassert(parent && H5T_COMPOUND == parent->shared->type); + HDassert(H5T_STATE_TRANSIENT == parent->shared->state); + HDassert(member); + HDassert(name && *name); /* Does NAME already exist in PARENT? */ - for (i=0; i<parent->shared->u.compnd.nmembs; i++) { - if (!HDstrcmp(parent->shared->u.compnd.memb[i].name, name)) + for(i = 0; i < parent->shared->u.compnd.nmembs; i++) + if(!HDstrcmp(parent->shared->u.compnd.memb[i].name, name)) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINSERT, FAIL, "member name is not unique") - } /* Does the new member overlap any existing member ? */ - total_size=member->shared->size; - for (i=0; i<parent->shared->u.compnd.nmembs; i++) { - if ((offset <= parent->shared->u.compnd.memb[i].offset && + total_size = member->shared->size; + for(i = 0; i < parent->shared->u.compnd.nmembs; i++) + if((offset <= parent->shared->u.compnd.memb[i].offset && offset + total_size > parent->shared->u.compnd.memb[i].offset) || (parent->shared->u.compnd.memb[i].offset <= offset && parent->shared->u.compnd.memb[i].offset + parent->shared->u.compnd.memb[i].size > offset)) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINSERT, FAIL, "member overlaps with another member") - } /* Does the new member overlap the end of the compound type? */ - if(offset+total_size>parent->shared->size) + if((offset + total_size) > parent->shared->size) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINSERT, FAIL, "member extends past end of compound type") /* Increase member array if necessary */ - if (parent->shared->u.compnd.nmembs >= parent->shared->u.compnd.nalloc) { - unsigned na = parent->shared->u.compnd.nalloc + H5T_COMPND_INC; - H5T_cmemb_t *x = H5MM_realloc (parent->shared->u.compnd.memb, - na * sizeof(H5T_cmemb_t)); + if(parent->shared->u.compnd.nmembs >= parent->shared->u.compnd.nalloc) { + unsigned na = MAX(1, parent->shared->u.compnd.nalloc * 2); + H5T_cmemb_t *x = H5MM_realloc(parent->shared->u.compnd.memb, na * sizeof(H5T_cmemb_t)); - if (!x) - HGOTO_ERROR (H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed") + if(!x) + HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed") parent->shared->u.compnd.nalloc = na; parent->shared->u.compnd.memb = x; - } + } /* end if */ /* Add member to end of member array */ idx = parent->shared->u.compnd.nmembs; parent->shared->u.compnd.memb[idx].name = H5MM_xstrdup(name); parent->shared->u.compnd.memb[idx].offset = offset; parent->shared->u.compnd.memb[idx].size = total_size; - parent->shared->u.compnd.memb[idx].type = H5T_copy (member, H5T_COPY_ALL); + parent->shared->u.compnd.memb[idx].type = H5T_copy(member, H5T_COPY_ALL); parent->shared->u.compnd.sorted = H5T_SORT_NONE; parent->shared->u.compnd.nmembs++; @@ -476,35 +470,42 @@ H5T_insert(const H5T_t *parent, const char *name, size_t offset, const H5T_t *me /* Determine if the compound datatype stayed packed */ if(parent->shared->u.compnd.packed) { /* Check if the member type is packed */ - if(H5T_is_packed(parent->shared->u.compnd.memb[idx].type)>0) { - if(idx==0) { + if(H5T_is_packed(parent->shared->u.compnd.memb[idx].type) > 0) { + if(idx == 0) { /* If the is the first member, the datatype is not packed * if the first member isn't at offset 0 */ - if(parent->shared->u.compnd.memb[idx].offset>0) - parent->shared->u.compnd.packed=FALSE; + if(parent->shared->u.compnd.memb[idx].offset > 0) + parent->shared->u.compnd.packed = FALSE; } /* end if */ else { /* If the is not the first member, the datatype is not * packed if the new member isn't adjoining the previous member */ - if(parent->shared->u.compnd.memb[idx].offset!=(parent->shared->u.compnd.memb[idx-1].offset+parent->shared->u.compnd.memb[idx-1].size)) - parent->shared->u.compnd.packed=FALSE; + if(parent->shared->u.compnd.memb[idx].offset != (parent->shared->u.compnd.memb[idx - 1].offset + parent->shared->u.compnd.memb[idx - 1].size)) + parent->shared->u.compnd.packed = FALSE; } /* end else */ } /* end if */ else - parent->shared->u.compnd.packed=FALSE; + parent->shared->u.compnd.packed = FALSE; } /* end if */ - /* - * Set the "force conversion" flag if the field's datatype indicates - */ - if(member->shared->force_conv==TRUE) - parent->shared->force_conv=TRUE; + /* Set the "force conversion" flag if the field's datatype indicates */ + if(member->shared->force_conv == TRUE) + parent->shared->force_conv = TRUE; + + /* Check for member having a later version than the parent */ + if(parent->shared->version < member->shared->version) + /* Upgrade parent datatype (and all other members also) */ + /* (can't use a partial datatype and later versions of the format are + * more efficient, so might as well upgrade all members also... -QAK) + */ + if(H5T_upgrade_version(parent, member->shared->version) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_CANTSET, FAIL, "can't upgrade member encoding version") done: FUNC_LEAVE_NOAPI(ret_value) -} +} /* end H5T_insert() */ /*------------------------------------------------------------------------- diff --git a/src/H5Tdbg.c b/src/H5Tdbg.c new file mode 100644 index 0000000..88e084d --- /dev/null +++ b/src/H5Tdbg.c @@ -0,0 +1,407 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by The HDF Group. * + * Copyright by the Board of Trustees of the University of Illinois. * + * All rights reserved. * + * * + * This file is part of HDF5. The full HDF5 copyright notice, including * + * terms governing use, modification, and redistribution, is contained in * + * the files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * Module Info: This module contains most of the "core" functionality of + * the H5T interface, including the API initialization code, etc. + * Many routines that are infrequently used, or are specialized for + * one particular datatype class are in another module. + */ + +/*------------------------------------------------------------------------- + * + * Created: H5Tdbg.c + * Jul 19 2007 + * Quincey Koziol <koziol@hdfgroup.org> + * + * Purpose: Dump debugging information about a datatype + * + *------------------------------------------------------------------------- + */ + +/****************/ +/* Module Setup */ +/****************/ + +#define H5T_PACKAGE /*suppress error about including H5Tpkg */ + + +/***********/ +/* Headers */ +/***********/ +#include "H5private.h" /* Generic Functions */ +#include "H5Eprivate.h" /* Error handling */ +#include "H5Tpkg.h" /* Datatypes */ + + +/****************/ +/* Local Macros */ +/****************/ + + +/******************/ +/* Local Typedefs */ +/******************/ + + +/********************/ +/* Package Typedefs */ +/********************/ + + +/********************/ +/* Local Prototypes */ +/********************/ + + +/*********************/ +/* Package Variables */ +/*********************/ + + +/*****************************/ +/* Library Private Variables */ +/*****************************/ + + +/*******************/ +/* Local Variables */ +/*******************/ + + + +/*------------------------------------------------------------------------- + * Function: H5T_print_stats + * + * Purpose: Print statistics about a conversion path. Statistics are + * printed only if all the following conditions are true: + * + * 1. The library was compiled with H5T_DEBUG defined. + * 2. Data type debugging is turned on at run time. + * 3. The path was called at least one time. + * + * The optional NPRINT argument keeps track of the number of + * conversions paths for which statistics have been shown. If + * its value is zero then table headers are printed before the + * first line of output. + * + * Return: Success: non-negative + * + * Failure: negative + * + * Programmer: Robb Matzke + * Monday, December 14, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5T_print_stats(H5T_path_t UNUSED * path, int UNUSED * nprint/*in,out*/) +{ +#ifdef H5T_DEBUG + hsize_t nbytes; + char bandwidth[32]; +#endif + + FUNC_ENTER_NOAPI_NOINIT_NOFUNC(H5T_print_stats) + +#ifdef H5T_DEBUG + if(H5DEBUG(T) && path->stats.ncalls > 0) { + if(nprint && 0 == (*nprint)++) { + HDfprintf(H5DEBUG(T), "H5T: type conversion statistics:\n"); + HDfprintf(H5DEBUG(T), " %-16s %10s %10s %8s %8s %8s %10s\n", + "Conversion", "Elmts", "Calls", "User", + "System", "Elapsed", "Bandwidth"); + HDfprintf(H5DEBUG(T), " %-16s %10s %10s %8s %8s %8s %10s\n", + "----------", "-----", "-----", "----", + "------", "-------", "---------"); + } + if(path->src && path->dst) + nbytes = MAX(H5T_get_size(path->src), H5T_get_size(path->dst)); + else if(path->src) + nbytes = H5T_get_size(path->src); + else if(path->dst) + nbytes = H5T_get_size(path->dst); + else + nbytes = 0; + nbytes *= path->stats.nelmts; + H5_bandwidth(bandwidth, (double)nbytes, path->stats.timer.etime); + HDfprintf(H5DEBUG(T), " %-16s %10Hd %10d %8.2f %8.2f %8.2f %10s\n", + path->name, + path->stats.nelmts, + path->stats.ncalls, + path->stats.timer.utime, + path->stats.timer.stime, + path->stats.timer.etime, + bandwidth); + } +#endif + FUNC_LEAVE_NOAPI(SUCCEED) +} /* end H5T_print_stats() */ + + +/*------------------------------------------------------------------------- + * Function: H5T_debug + * + * Purpose: Prints information about a data type. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Robb Matzke + * Wednesday, January 7, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5T_debug(const H5T_t *dt, FILE *stream) +{ + const char *s1 = "", *s2 = ""; + unsigned i; + + FUNC_ENTER_NOAPI_NOFUNC(H5T_debug) + + /* Check args */ + HDassert(dt); + HDassert(stream); + + switch(dt->shared->type) { + case H5T_INTEGER: + s1 = "int"; + break; + + case H5T_FLOAT: + s1 = "float"; + break; + + case H5T_TIME: + s1 = "time"; + break; + + case H5T_STRING: + s1 = "str"; + break; + + case H5T_BITFIELD: + s1 = "bits"; + break; + + case H5T_OPAQUE: + s1 = "opaque"; + break; + + case H5T_COMPOUND: + s1 = "struct"; + break; + + case H5T_ENUM: + s1 = "enum"; + break; + + case H5T_VLEN: + if(H5T_IS_VL_STRING(dt->shared)) + s1 = "str"; + else + s1 = "vlen"; + break; + + default: + s1 = ""; + break; + } /* end switch */ + + switch(dt->shared->state) { + case H5T_STATE_TRANSIENT: + s2 = "[transient]"; + break; + + case H5T_STATE_RDONLY: + s2 = "[constant]"; + break; + + case H5T_STATE_IMMUTABLE: + s2 = "[predefined]"; + break; + + case H5T_STATE_NAMED: + s2 = "[named,closed]"; + break; + + case H5T_STATE_OPEN: + s2 = "[named,open]"; + break; + } /* end switch */ + + fprintf(stream, "%s%s {nbytes=%lu", s1, s2, (unsigned long)(dt->shared->size)); + + if(H5T_IS_ATOMIC(dt->shared)) { + uint64_t tmp; + + switch(dt->shared->u.atomic.order) { + case H5T_ORDER_BE: + s1 = "BE"; + break; + + case H5T_ORDER_LE: + s1 = "LE"; + break; + + case H5T_ORDER_VAX: + s1 = "VAX"; + break; + + case H5T_ORDER_NONE: + s1 = "NONE"; + break; + + default: + s1 = "order?"; + break; + } /* end switch */ + + fprintf(stream, ", %s", s1); + + if(dt->shared->u.atomic.offset) + fprintf(stream, ", offset=%lu", + (unsigned long) (dt->shared->u.atomic.offset)); + if(dt->shared->u.atomic.prec != 8 * dt->shared->size) + fprintf(stream, ", prec=%lu", + (unsigned long) (dt->shared->u.atomic.prec)); + switch(dt->shared->type) { + case H5T_INTEGER: + switch(dt->shared->u.atomic.u.i.sign) { + case H5T_SGN_NONE: + s1 = "unsigned"; + break; + + case H5T_SGN_2: + s1 = NULL; + break; + + default: + s1 = "sign?"; + break; + + } /* end switch */ + if(s1) + fprintf(stream, ", %s", s1); + break; + + case H5T_FLOAT: + switch(dt->shared->u.atomic.u.f.norm) { + case H5T_NORM_IMPLIED: + s1 = "implied"; + break; + + case H5T_NORM_MSBSET: + s1 = "msbset"; + break; + + case H5T_NORM_NONE: + s1 = "no-norm"; + break; + + default: + s1 = "norm?"; + break; + } /* end switch */ + + fprintf(stream, ", sign=%lu+1", + (unsigned long)(dt->shared->u.atomic.u.f.sign)); + fprintf(stream, ", mant=%lu+%lu (%s)", + (unsigned long)(dt->shared->u.atomic.u.f.mpos), + (unsigned long)(dt->shared->u.atomic.u.f.msize), s1); + fprintf(stream, ", exp=%lu+%lu", + (unsigned long)(dt->shared->u.atomic.u.f.epos), + (unsigned long)(dt->shared->u.atomic.u.f.esize)); + tmp = dt->shared->u.atomic.u.f.ebias >> 32; + if(tmp) { + size_t hi = (size_t)tmp; + size_t lo = (size_t)(dt->shared->u.atomic.u.f.ebias & 0xffffffff); + fprintf(stream, " bias=0x%08lx%08lx", + (unsigned long)hi, (unsigned long)lo); + } else { + size_t lo = (size_t)(dt->shared->u.atomic.u.f.ebias & 0xffffffff); + fprintf(stream, " bias=0x%08lx", (unsigned long)lo); + } + break; + + default: + /* No additional info */ + break; + } /* end switch */ + } else if(H5T_COMPOUND == dt->shared->type) { + /* Compound data type */ + for(i = 0; i < dt->shared->u.compnd.nmembs; i++) { + fprintf(stream, "\n\"%s\" @%lu", + dt->shared->u.compnd.memb[i].name, + (unsigned long)(dt->shared->u.compnd.memb[i].offset)); + fprintf(stream, " "); + H5T_debug(dt->shared->u.compnd.memb[i].type, stream); + } /* end for */ + fprintf(stream, "\n"); + } else if(H5T_VLEN == dt->shared->type) { + switch(dt->shared->u.vlen.loc) { + case H5T_LOC_MEMORY: + fprintf(stream, ", loc=memory"); + break; + + case H5T_LOC_DISK: + fprintf(stream, ", loc=disk"); + break; + + default: + fprintf(stream, ", loc=UNKNOWN"); + break; + } /* end switch */ + + if(H5T_IS_VL_STRING(dt->shared)) + /* Variable length string datatype */ + fprintf(stream, ", variable-length"); + else { + /* Variable length sequence datatype */ + fprintf(stream, " VLEN "); + H5T_debug(dt->shared->parent, stream); + fprintf(stream, "\n"); + } /* end else */ + } else if(H5T_ENUM == dt->shared->type) { + size_t base_size; + + /* Enumeration data type */ + fprintf(stream, " "); + H5T_debug(dt->shared->parent, stream); + base_size = dt->shared->parent->shared->size; + for(i = 0; i < dt->shared->u.enumer.nmembs; i++) { + size_t k; + + fprintf(stream, "\n\"%s\" = 0x", dt->shared->u.enumer.name[i]); + for(k = 0; k < base_size; k++) + fprintf(stream, "%02lx", + (unsigned long)(dt->shared->u.enumer.value + (i * base_size) + k)); + } /* end for */ + fprintf(stream, "\n"); + } else if(H5T_OPAQUE == dt->shared->type) { + fprintf(stream, ", tag=\"%s\"", dt->shared->u.opaque.tag); + } else { + /* Unknown */ + fprintf(stream, "unknown class %d\n", (int)(dt->shared->type)); + } + fprintf(stream, "}"); + + FUNC_LEAVE_NOAPI(SUCCEED) +} /* end H5T_debug() */ + diff --git a/src/H5Titerate.c b/src/H5Titerate.c new file mode 100644 index 0000000..15a91e3 --- /dev/null +++ b/src/H5Titerate.c @@ -0,0 +1,155 @@ +/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * + * Copyright by The HDF Group. * + * Copyright by the Board of Trustees of the University of Illinois. * + * All rights reserved. * + * * + * This file is part of HDF5. The full HDF5 copyright notice, including * + * terms governing use, modification, and redistribution, is contained in * + * the files COPYING and Copyright.html. COPYING can be found at the root * + * of the source code distribution tree; Copyright.html can be found at the * + * root level of an installed copy of the electronic HDF5 document set and * + * is linked from the top-level documents page. It can also be found at * + * http://hdfgroup.org/HDF5/doc/Copyright.html. If you do not have * + * access to either file, you may request a copy from help@hdfgroup.org. * + * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */ + +/* + * Module Info: This module contains most of the "core" functionality of + * the H5T interface, including the API initialization code, etc. + * Many routines that are infrequently used, or are specialized for + * one particular datatype class are in another module. + */ + +/*------------------------------------------------------------------------- + * + * Created: H5Tdbg.c + * Jul 19 2007 + * Quincey Koziol <koziol@hdfgroup.org> + * + * Purpose: Dump debugging information about a datatype + * + *------------------------------------------------------------------------- + */ + +/****************/ +/* Module Setup */ +/****************/ + +#define H5T_PACKAGE /*suppress error about including H5Tpkg */ + + +/***********/ +/* Headers */ +/***********/ +#include "H5private.h" /* Generic Functions */ +#include "H5Eprivate.h" /* Error handling */ +#include "H5Tpkg.h" /* Datatypes */ + + +/****************/ +/* Local Macros */ +/****************/ + + +/******************/ +/* Local Typedefs */ +/******************/ + + +/********************/ +/* Package Typedefs */ +/********************/ + + +/********************/ +/* Local Prototypes */ +/********************/ + + +/*********************/ +/* Package Variables */ +/*********************/ + + +/*****************************/ +/* Library Private Variables */ +/*****************************/ + + +/*******************/ +/* Local Variables */ +/*******************/ + + + +/*------------------------------------------------------------------------- + * Function: H5T_visit + * + * Purpose: Visit a datatype and all it's members and/or parents, making + * a callback for each. + * + * Return: Non-negative on success/Negative on failure + * + * Programmer: Quincey Koziol + * Thursday, July 19, 2007 + * + *------------------------------------------------------------------------- + */ +herr_t +H5T_visit(H5T_t *dt, unsigned visit_flags, H5T_operator_t op, void *op_value) +{ + hbool_t is_complex; /* Flag indicating current datatype is "complex" */ + herr_t ret_value = SUCCEED; /* Return value */ + + FUNC_ENTER_NOAPI(H5T_visit, FAIL) + + /* Sanity check */ + HDassert(dt); + HDassert(op); + + /* Check for complex datatype */ + is_complex = H5T_IS_COMPLEX(dt->shared->type); + + /* If the callback is to be made on the datatype first, do that */ + if(is_complex && (visit_flags & H5T_VISIT_COMPLEX_FIRST)) + if(op(dt, op_value) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "operator callback failed") + + /* Make callback for each member/child, if requested */ + switch(dt->shared->type) { + case H5T_COMPOUND: + { + unsigned u; /* Local index variable */ + + /* Visit each member of the compound datatype */ + for(u = 0; u < dt->shared->u.compnd.nmembs; u++) + if(H5T_visit(dt->shared->u.compnd.memb[u].type, visit_flags, op, op_value) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "can't visit member datatype") + } /* end case */ + break; + + case H5T_ARRAY: + case H5T_VLEN: + case H5T_ENUM: + /* Visit parent type */ + if(H5T_visit(dt->shared->parent, visit_flags, op, op_value) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "can't visit parent datatype") + break; + + default: + /* Visit "simple" datatypes here */ + if(visit_flags & H5T_VISIT_SIMPLE) + if(op(dt, op_value) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "operator callback failed") + break; + } /* end switch */ + + /* If the callback is to be made on the datatype last, do that */ + if(is_complex && (visit_flags & H5T_VISIT_COMPLEX_LAST)) + if(op(dt, op_value) < 0) + HGOTO_ERROR(H5E_DATATYPE, H5E_BADITER, FAIL, "operator callback failed") + +done: + FUNC_LEAVE_NOAPI(ret_value) +} /* end H5T_iterate() */ + diff --git a/src/H5Tpkg.h b/src/H5Tpkg.h index 6b68bf1..4704288 100644 --- a/src/H5Tpkg.h +++ b/src/H5Tpkg.h @@ -68,6 +68,45 @@ #define H5T_IS_ATOMIC(dt) (!(H5T_IS_COMPLEX((dt)->type) || (dt)->type==H5T_OPAQUE)) +/* + * Datatype encoding versions + */ + +/* This is the version to create all datatypes which don't contain + * array datatypes (atomic types, compound datatypes without array fields, + * vlen sequences of objects which aren't arrays, etc.) or VAX byte-ordered + * objects. + */ +#define H5O_DTYPE_VERSION_1 1 + +/* This is the version to create all datatypes which contain H5T_ARRAY + * class objects (array definitely, potentially compound & vlen sequences also), + * but not VAX byte-ordered objects. + */ +#define H5O_DTYPE_VERSION_2 2 + +/* This is the version to create all datatypes which contain VAX byte-ordered + * objects (floating-point types, currently). + */ +/* This version also packs compound & enum field names without padding */ +/* This version also encodes the member offset of compound fields more efficiently */ +/* This version also encodes array types more efficiently */ +#define H5O_DTYPE_VERSION_3 3 + +/* The latest version of the format. Look through the 'encode helper' routine + * and 'size' callback for places to change when updating this. */ +#define H5O_DTYPE_VERSION_LATEST H5O_DTYPE_VERSION_3 + + +/* Flags for visiting datatype */ +#define H5T_VISIT_COMPLEX_FIRST 0x01 /* Visit complex datatype before visiting member/parent datatypes */ +#define H5T_VISIT_COMPLEX_LAST 0x02 /* Visit complex datatype after visiting member/parent datatypes */ + /* (setting both flags will mean visiting complex type twice) */ +#define H5T_VISIT_SIMPLE 0x04 /* Visit simple datatypes (at all) */ + /* (setting H5T_VISIT_SIMPLE and _not_ setting either H5T_VISIT_COMPLEX_FIRST or H5T_VISIT_COMPLEX_LAST will mean visiting _only_ "simple" "leafs" in the "tree" */ + /* (_not_ setting H5T_VISIT_SIMPLE and setting either H5T_VISIT_COMPLEX_FIRST or H5T_VISIT_COMPLEX_LAST will mean visiting all nodes _except_ "simple" "leafs" in the "tree" */ + + /* Define an internal macro for converting between floating number(float and double) and floating number. * All Cray compilers don't support denormalized floating values generating exception(?). */ #if H5_CONVERT_DENORMAL_FLOAT @@ -314,6 +353,7 @@ typedef struct H5T_shared_t { H5T_state_t state; /*current state of the type */ H5T_class_t type; /*which class of type is this? */ size_t size; /*total size of an instance of this type */ + unsigned version; /* Version of object header message to encode this object with */ hbool_t force_conv;/* Set if this type always needs to be converted and H5T_conv_noop cannot be called */ struct H5T_t *parent;/*parent type for derived datatypes */ union { @@ -362,6 +402,9 @@ typedef struct { hid_t tcpl_id; /* Named datatype creation property list */ } H5T_obj_create_t; +/* Typedef for datatype iteration operations */ +typedef herr_t (*H5T_operator_t)(H5T_t *dt, void *op_data/*in,out*/); + /* * Alignment information for native types. A value of N indicates that the * data must be aligned on an address ADDR such that 0 == ADDR mod N. When @@ -458,20 +501,11 @@ H5_DLL herr_t H5T_commit_named(const H5G_loc_t *loc, const char *name, H5T_t *dt, hid_t lcpl_id, hid_t tcpl_id, hid_t tapl_id, hid_t dxpl_id); H5_DLL H5T_t *H5T_alloc(void); H5_DLL herr_t H5T_free(H5T_t *dt); -H5_DLL H5T_sign_t H5T_get_sign(H5T_t const *dt); +H5_DLL herr_t H5T_visit(H5T_t *dt, unsigned visit_flags, H5T_operator_t op, + void *op_value); H5_DLL H5T_t *H5T_get_super(H5T_t *dt); -H5_DLL char *H5T_get_member_name(H5T_t const *dt, unsigned membno); -H5_DLL herr_t H5T_get_member_value(const H5T_t *dt, unsigned membno, void *value); -H5_DLL int H5T_get_nmembers(const H5T_t *dt); -H5_DLL herr_t H5T_insert(const H5T_t *parent, const char *name, size_t offset, - const H5T_t *member); -H5_DLL H5T_t *H5T_enum_create(const H5T_t *parent); -H5_DLL herr_t H5T_enum_insert(const H5T_t *dt, const char *name, const void *value); -H5_DLL int H5T_get_array_ndims(H5T_t *dt); -H5_DLL int H5T_get_array_dims(H5T_t *dt, hsize_t dims[]); -H5_DLL herr_t H5T_sort_value(const H5T_t *dt, int *map); -H5_DLL herr_t H5T_sort_name(const H5T_t *dt, int *map); H5_DLL herr_t H5T_set_size(H5T_t *dt, size_t size); +H5_DLL herr_t H5T_upgrade_version(H5T_t *dt, unsigned new_version); /* Conversion functions */ H5_DLL herr_t H5T_conv_noop(hid_t src_id, hid_t dst_id, H5T_cdata_t *cdata, @@ -1326,6 +1360,9 @@ H5_DLL htri_t H5T_bit_inc(uint8_t *buf, size_t start, size_t size); H5_DLL htri_t H5T_bit_dec(uint8_t *buf, size_t start, size_t size); H5_DLL void H5T_bit_neg(uint8_t *buf, size_t start, size_t size); +/* Fixed-point functions */ +H5_DLL H5T_sign_t H5T_get_sign(H5T_t const *dt); + /* VL functions */ H5_DLL H5T_t * H5T_vlen_create(const H5T_t *base); H5_DLL htri_t H5T_vlen_set_loc(const H5T_t *dt, H5F_t *f, H5T_loc_t loc); @@ -1333,13 +1370,31 @@ H5_DLL htri_t H5T_vlen_set_loc(const H5T_t *dt, H5F_t *f, H5T_loc_t loc); /* Array functions */ H5_DLL H5T_t * H5T_array_create(H5T_t *base, unsigned ndims, const hsize_t dim[/* ndims */]); +H5_DLL int H5T_get_array_ndims(const H5T_t *dt); +H5_DLL int H5T_get_array_dims(const H5T_t *dt, hsize_t dims[]); /* Compound functions */ +H5_DLL herr_t H5T_insert(H5T_t *parent, const char *name, size_t offset, + const H5T_t *member); H5_DLL H5T_t *H5T_get_member_type(const H5T_t *dt, unsigned membno); H5_DLL size_t H5T_get_member_offset(const H5T_t *dt, unsigned membno); H5_DLL size_t H5T_get_member_size(const H5T_t *dt, unsigned membno); H5_DLL htri_t H5T_is_packed(const H5T_t *dt); H5_DLL H5T_subset_t H5T_conv_struct_subset(const H5T_cdata_t *cdata); +/* Enumerated type functions */ +H5_DLL H5T_t *H5T_enum_create(const H5T_t *parent); +H5_DLL herr_t H5T_enum_insert(const H5T_t *dt, const char *name, const void *value); +H5_DLL herr_t H5T_get_member_value(const H5T_t *dt, unsigned membno, void *value); + +/* Field functions (for both compound & enumerated types) */ +H5_DLL char *H5T_get_member_name(H5T_t const *dt, unsigned membno); +H5_DLL int H5T_get_nmembers(const H5T_t *dt); +H5_DLL herr_t H5T_sort_value(const H5T_t *dt, int *map); +H5_DLL herr_t H5T_sort_name(const H5T_t *dt, int *map); + +/* Debugging functions */ +H5_DLL herr_t H5T_print_stats(H5T_path_t *path, int *nprint/*in,out*/); + #endif /* _H5Tpkg_H */ diff --git a/src/H5Tprivate.h b/src/H5Tprivate.h index 842eced..deeb8ce 100644 --- a/src/H5Tprivate.h +++ b/src/H5Tprivate.h @@ -114,6 +114,7 @@ H5_DLL herr_t H5T_vlen_get_alloc_info(hid_t dxpl_id, H5T_vlen_alloc_info_t **vl_ H5_DLL htri_t H5T_set_loc(H5T_t *dt, H5F_t *f, H5T_loc_t loc); H5_DLL htri_t H5T_is_sensible(const H5T_t *dt); H5_DLL uint32_t H5T_hash(H5F_t * file, const H5T_t *dt); +H5_DLL herr_t H5T_set_latest_version(H5T_t *dt); /* Reference specific functions */ H5_DLL H5R_type_t H5T_get_ref_type(const H5T_t *dt); diff --git a/src/H5Tvlen.c b/src/H5Tvlen.c index 1d71498..bbc698f 100644 --- a/src/H5Tvlen.c +++ b/src/H5Tvlen.c @@ -115,20 +115,20 @@ H5Tvlen_create(hid_t base_id) H5TRACE1("i", "i", base_id); /* Check args */ - if (NULL==(base=H5I_object_verify(base_id,H5I_DATATYPE))) + if(NULL == (base = H5I_object_verify(base_id, H5I_DATATYPE))) HGOTO_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not an valid base datatype") /* Create up VL datatype */ - if ((dt=H5T_vlen_create(base))==NULL) + if((dt = H5T_vlen_create(base)) == NULL) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "invalid VL location") /* Atomize the type */ - if ((ret_value=H5I_register(H5I_DATATYPE, dt))<0) + if((ret_value = H5I_register(H5I_DATATYPE, dt)) < 0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTREGISTER, FAIL, "unable to register datatype") done: FUNC_LEAVE_API(ret_value) -} +} /* end H5Tvlen_create() */ /*------------------------------------------------------------------------- @@ -157,7 +157,7 @@ H5T_vlen_create(const H5T_t *base) FUNC_ENTER_NOAPI_NOINIT(H5T_vlen_create) /* Check args */ - assert(base); + HDassert(base); /* Build new type */ if(NULL == (dt = H5T_alloc())) @@ -171,19 +171,22 @@ H5T_vlen_create(const H5T_t *base) dt->shared->force_conv = TRUE; dt->shared->parent = H5T_copy(base, H5T_COPY_ALL); + /* Inherit encoding version from base type */ + dt->shared->version = base->shared->version; + /* This is a sequence, not a string */ dt->shared->u.vlen.type = H5T_VLEN_SEQUENCE; /* Set up VL information */ - if (H5T_set_loc(dt, NULL, H5T_LOC_MEMORY)<0) + if(H5T_set_loc(dt, NULL, H5T_LOC_MEMORY) < 0) HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, NULL, "invalid datatype location") /* Set return value */ - ret_value=dt; + ret_value = dt; done: FUNC_LEAVE_NOAPI(ret_value) -} +} /* end H5T_vlen_create() */ /*------------------------------------------------------------------------- @@ -284,7 +287,7 @@ H5T_vlen_set_loc(const H5T_t *dt, H5F_t *f, H5T_loc_t loc) break; default: - HGOTO_ERROR (H5E_DATATYPE, H5E_BADRANGE, FAIL, "invalid VL datatype location") + HGOTO_ERROR(H5E_DATATYPE, H5E_BADRANGE, FAIL, "invalid VL datatype location") } /* end switch */ /*lint !e788 All appropriate cases are covered */ } /* end if */ diff --git a/src/Makefile.am b/src/Makefile.am index bef62b6..b52afbc 100755 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -78,10 +78,12 @@ libhdf5_la_SOURCES= H5.c H5checksum.c H5dbg.c H5system.c H5timer.c H5trace.c \ H5R.c H5RC.c \ H5RS.c H5S.c H5Sall.c H5Shyper.c H5Smpio.c H5Snone.c H5Spoint.c \ H5Sselect.c H5Stest.c H5SL.c H5SM.c H5SMbtree2.c \ - H5SMcache.c H5SMtest.c H5ST.c H5T.c H5Tarray.c H5Tbit.c H5Tcommit.c \ - H5Tcompound.c H5Tconv.c H5Tcset.c H5Tdeprec.c H5Tenum.c H5Tfields.c \ + H5SMcache.c H5SMtest.c H5ST.c \ + H5T.c H5Tarray.c H5Tbit.c H5Tcommit.c H5Tcompound.c H5Tconv.c \ + H5Tcset.c H5Tdbg.c H5Tdeprec.c H5Tenum.c H5Tfields.c \ H5Tfixed.c \ - H5Tfloat.c H5Tinit.c H5Tnative.c H5Toffset.c H5Toh.c H5Topaque.c \ + H5Tfloat.c H5Tinit.c H5Titerate.c H5Tnative.c H5Toffset.c H5Toh.c \ + H5Topaque.c \ H5Torder.c \ H5Tpad.c H5Tprecis.c H5Tstrpad.c H5Tvlen.c H5TS.c H5V.c H5WB.c H5Z.c \ H5Zdeflate.c H5Zfletcher32.c H5Znbit.c H5Zshuffle.c H5Zszip.c \ diff --git a/src/Makefile.in b/src/Makefile.in index 1f82a69..ce657cf 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -111,9 +111,9 @@ am_libhdf5_la_OBJECTS = H5.lo H5checksum.lo H5dbg.lo H5system.lo \ H5S.lo H5Sall.lo H5Shyper.lo H5Smpio.lo H5Snone.lo H5Spoint.lo \ H5Sselect.lo H5Stest.lo H5SL.lo H5SM.lo H5SMbtree2.lo \ H5SMcache.lo H5SMtest.lo H5ST.lo H5T.lo H5Tarray.lo H5Tbit.lo \ - H5Tcommit.lo H5Tcompound.lo H5Tconv.lo H5Tcset.lo H5Tdeprec.lo \ + H5Tcommit.lo H5Tcompound.lo H5Tconv.lo H5Tcset.lo H5Tdbg.lo H5Tdeprec.lo \ H5Tenum.lo H5Tfields.lo H5Tfixed.lo H5Tfloat.lo H5Tinit.lo \ - H5Tnative.lo H5Toffset.lo H5Toh.lo H5Topaque.lo H5Torder.lo \ + H5Titerate.lo H5Tnative.lo H5Toffset.lo H5Toh.lo H5Topaque.lo H5Torder.lo \ H5Tpad.lo H5Tprecis.lo H5Tstrpad.lo H5Tvlen.lo H5TS.lo H5V.lo \ H5WB.lo H5Z.lo H5Zdeflate.lo H5Zfletcher32.lo H5Znbit.lo \ H5Zshuffle.lo H5Zszip.lo H5Zscaleoffset.lo H5Ztrans.lo @@ -434,9 +434,9 @@ libhdf5_la_SOURCES = H5.c H5checksum.c H5dbg.c H5system.c H5timer.c H5trace.c \ H5RS.c H5S.c H5Sall.c H5Shyper.c H5Smpio.c H5Snone.c H5Spoint.c \ H5Sselect.c H5Stest.c H5SL.c H5SM.c H5SMbtree2.c \ H5SMcache.c H5SMtest.c H5ST.c H5T.c H5Tarray.c H5Tbit.c H5Tcommit.c \ - H5Tcompound.c H5Tconv.c H5Tcset.c H5Tdeprec.c H5Tenum.c H5Tfields.c \ + H5Tcompound.c H5Tconv.c H5Tcset.c H5Tdbg.c H5Tdeprec.c H5Tenum.c H5Tfields.c \ H5Tfixed.c \ - H5Tfloat.c H5Tinit.c H5Tnative.c H5Toffset.c H5Toh.c H5Topaque.c \ + H5Tfloat.c H5Tinit.c H5Titerate.c H5Tnative.c H5Toffset.c H5Toh.c H5Topaque.c \ H5Torder.c \ H5Tpad.c H5Tprecis.c H5Tstrpad.c H5Tvlen.c H5TS.c H5V.c H5WB.c H5Z.c \ H5Zdeflate.c H5Zfletcher32.c H5Znbit.c H5Zshuffle.c H5Zszip.c \ @@ -745,12 +745,14 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tcompound.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tconv.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tcset.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tdbg.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tdeprec.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tenum.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tfields.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tfixed.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tfloat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tinit.Plo@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Titerate.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Tnative.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Toffset.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/H5Toh.Plo@am__quote@ |