diff options
author | Robb Matzke <matzke@llnl.gov> | 1998-04-28 13:59:08 (GMT) |
---|---|---|
committer | Robb Matzke <matzke@llnl.gov> | 1998-04-28 13:59:08 (GMT) |
commit | 66071d5078ad9841c8fbb430881ae2c6e059886e (patch) | |
tree | 163bf340ff1c2dcc9aebc35a1bea296a8da0e623 /src | |
parent | 4dcf59ae4461eec74a180d77783d9064d2aa3a58 (diff) | |
download | hdf5-66071d5078ad9841c8fbb430881ae2c6e059886e.zip hdf5-66071d5078ad9841c8fbb430881ae2c6e059886e.tar.gz hdf5-66071d5078ad9841c8fbb430881ae2c6e059886e.tar.bz2 |
[svn-r377] Changes since 19980424
----------------------
./src/H5A.c
./src/H5T.c
Fixed memory leaks. More to come later but PureAtria doesn't
make a Linux version of purify and the free version doesn't
compile with the new SMP Linux kernels so I had to debug over
the internet on a day that Sprint seemed to be having routing
problems... oh well. I got rid of most of the leaks.
./src/H5Apublic.h
Includes H5Ipublic.h for types in the header file.
./src/H5O.c
Comments improved for H5O_read()
./test/tattr.c
Removed a non-ANSI empty initializer.
./test/dsets.c
Include <string.h>
./test/istore.c
Fixed a non-ANSI pointer conversion.
Diffstat (limited to 'src')
-rw-r--r-- | src/H5A.c | 155 | ||||
-rw-r--r-- | src/H5Apublic.h | 2 | ||||
-rw-r--r-- | src/H5F.c | 4 | ||||
-rw-r--r-- | src/H5Ffamily.c | 27 | ||||
-rw-r--r-- | src/H5Fsplit.c | 443 | ||||
-rw-r--r-- | src/H5I.c | 1 | ||||
-rw-r--r-- | src/H5O.c | 6 | ||||
-rw-r--r-- | src/H5P.c | 36 | ||||
-rw-r--r-- | src/H5T.c | 57 |
9 files changed, 586 insertions, 145 deletions
@@ -105,6 +105,7 @@ H5A_init_interface(void) static void H5A_term_interface(void) { + H5I_destroy_group (H5_ATTR); } @@ -213,14 +214,13 @@ H5Acreate(hid_t loc_id, const char *name, hid_t datatype, hid_t dataspace, * April 2, 1998 * * Modifications: - * *------------------------------------------------------------------------- */ static hid_t H5A_create(const H5G_entry_t *ent, const char *name, const H5T_t *type, const H5S_t *space) { H5A_t *attr = NULL; - H5A_t *found_attr = NULL; + H5A_t found_attr; intn seq=0; hid_t ret_value = FAIL; @@ -256,14 +256,19 @@ H5A_create(const H5G_entry_t *ent, const char *name, const H5T_t *type, const H5 /* Read in the existing attributes to check for duplicates */ seq=0; - while((found_attr=H5O_read(&(attr->ent), H5O_ATTR, seq, NULL))!=NULL) - { - /* Compare found attribute name to new attribute name reject creation if names are the same */ - if(HDstrcmp(found_attr->name,attr->name)==0) - HGOTO_ERROR(H5E_ATTR, H5E_CANTCREATE, FAIL, - "attribute already exists"); - seq++; - } /* end while */ + while(H5O_read(&(attr->ent), H5O_ATTR, seq, &found_attr)!=NULL) { + /* + * Compare found attribute name to new attribute name reject creation + * if names are the same. + */ + if(HDstrcmp(found_attr.name,attr->name)==0) { + H5O_reset (H5O_ATTR, &found_attr); + HGOTO_ERROR(H5E_ATTR, H5E_CANTCREATE, FAIL, + "attribute already exists"); + } + H5O_reset (H5O_ATTR, &found_attr); + seq++; + } /* end while */ /* Create the attribute message and save the attribute index */ if (H5O_modify(&(attr->ent), H5O_ATTR, H5O_NEW_MESG, 0, attr) < 0) @@ -309,8 +314,8 @@ done: static int H5A_get_index(H5G_entry_t *ent, const char *name) { - H5A_t *found_attr = NULL; - int ret_value = FAIL; + H5A_t found_attr; + int ret_value=FAIL, i; FUNC_ENTER(H5A_get_index, FAIL); @@ -318,18 +323,25 @@ H5A_get_index(H5G_entry_t *ent, const char *name) assert(name); /* Look up the attribute for the object */ - ret_value=0; - while((found_attr=H5O_read(ent, H5O_ATTR, ret_value, NULL))!=NULL) - { - /* Compare found attribute name to new attribute name reject creation if names are the same */ - if(HDstrcmp(found_attr->name,name)==0) - break; - ret_value++; - } /* end while */ - if(found_attr==NULL) { + i=0; + while(H5O_read(ent, H5O_ATTR, i, &found_attr)!=NULL) { + /* + * Compare found attribute name to new attribute name reject creation + * if names are the same. + */ + if(HDstrcmp(found_attr.name,name)==0) { + H5O_reset (H5O_ATTR, &found_attr); + ret_value = i; + break; + } + H5O_reset (H5O_ATTR, &found_attr); + i++; + } /* end while */ + + if(ret_value<0) { HRETURN_ERROR(H5E_ATTR, H5E_NOTFOUND, FAIL, "attribute not found"); - } + } FUNC_LEAVE(ret_value); } /* H5A_get_index() */ @@ -479,13 +491,8 @@ H5A_open(H5G_entry_t *ent, unsigned idx) /* check args */ assert(ent); - /* Build the attribute information */ - if((attr = H5MM_xcalloc(1, sizeof(H5A_t)))==NULL) - HRETURN_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, - "unable to allocate space for attribute info"); - /* Read in attribute with H5O_read() */ - if (NULL==(H5O_read(ent, H5O_ATTR, idx, attr))) { + if (NULL==(attr=H5O_read(ent, H5O_ATTR, idx, attr))) { HGOTO_ERROR(H5E_ATTR, H5E_CANTINIT, FAIL, "unable to load attribute info from dataset header"); } @@ -1077,7 +1084,7 @@ H5Aiterate(hid_t loc_id, unsigned *attr_num, H5A_operator_t op, void *op_data) { H5G_entry_t *ent = NULL; /* Symbol table entry of object to attribute */ void *obj = NULL; - H5A_t *found_attr = NULL; + H5A_t found_attr; int ret_value = 0; FUNC_ENTER(H5Anum_attrs, FAIL); @@ -1105,12 +1112,15 @@ H5Aiterate(hid_t loc_id, unsigned *attr_num, H5A_operator_t op, void *op_data) /* Look up the attribute for the object */ if((int)*attr_num<H5O_count(ent, H5O_ATTR)) /* Make certain the start point is reasonable */ - while((found_attr=H5O_read(ent, H5O_ATTR, *attr_num, NULL))!=NULL) + while(H5O_read(ent, H5O_ATTR, *attr_num, &found_attr)!=NULL) { /* Compare found attribute name to new attribute name reject creation if names are the same */ (*attr_num)++; - if((ret_value=op(loc_id,found_attr->name,op_data))!=0) + if((ret_value=op(loc_id,found_attr.name,op_data))!=0) { + H5O_reset (H5O_ATTR, &found_attr); break; + } + H5O_reset (H5O_ATTR, &found_attr); } /* end while */ FUNC_LEAVE(ret_value); @@ -1140,11 +1150,11 @@ H5Aiterate(hid_t loc_id, unsigned *attr_num, H5A_operator_t op, void *op_data) herr_t H5Adelete(hid_t loc_id, const char *name) { - H5A_t *found_attr = NULL; + H5A_t found_attr; H5G_entry_t *ent = NULL; /* Symbol table entry of object to attribute */ void *obj = NULL; - intn idx=0; - hid_t ret_value = FAIL; + intn idx=0, found=-1; + herr_t ret_value = FAIL; FUNC_ENTER(H5Aopen_name, FAIL); @@ -1168,20 +1178,26 @@ H5Adelete(hid_t loc_id, const char *name) /* Look up the attribute for the object */ idx=0; - while((found_attr=H5O_read(ent, H5O_ATTR, idx, NULL))!=NULL) - { - /* Compare found attribute name to new attribute name reject creation if names are the same */ - if(HDstrcmp(found_attr->name,name)==0) - break; - idx++; - } /* end while */ - if(found_attr==NULL) { + while(H5O_read(ent, H5O_ATTR, idx, &found_attr)!=NULL) { + /* + * Compare found attribute name to new attribute name reject + * creation if names are the same. + */ + if(HDstrcmp(found_attr.name,name)==0) { + H5O_reset (H5O_ATTR, &found_attr); + found = idx; + break; + } + H5O_reset (H5O_ATTR, &found_attr); + idx++; + } /* end while */ + if (found<0) { HRETURN_ERROR(H5E_ATTR, H5E_NOTFOUND, FAIL, "attribute not found"); - } + } /* Delete the attribute from the location */ - if ((ret_value=H5O_remove(ent, H5O_ATTR, idx)) < 0) + if ((ret_value=H5O_remove(ent, H5O_ATTR, found)) < 0) HRETURN_ERROR(H5E_ATTR, H5E_CANTDELETE, FAIL, "can't delete attribute header message"); @@ -1209,41 +1225,17 @@ H5Adelete(hid_t loc_id, const char *name) herr_t H5Aclose(hid_t attr_id) { - H5A_t *attr = NULL; - herr_t ret_value = FAIL; - FUNC_ENTER(H5Aclose, FAIL); /* check arguments */ if (H5_ATTR != H5I_group(attr_id) || - (NULL == (attr = H5I_object(attr_id)))) { + NULL == H5I_object(attr_id)) { HRETURN_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not an attribute"); } - /* Check if the attribute has any data yet, if not, fill with zeroes */ - if(!attr->initialized) { - uint8 *tmp_buf=H5MM_xcalloc(1,attr->data_size); - - if (NULL == tmp_buf) { - HRETURN_ERROR(H5E_ATTR, H5E_NOSPACE, FAIL, - "can't allocate attribute fill-value"); - } - - /* Go write the fill data to the attribute */ - if ((ret_value=H5A_write(attr,attr->dt,tmp_buf))<0) { - HRETURN_ERROR(H5E_ATTR, H5E_WRITEERROR, FAIL, - "can't write attribute"); - } - - /* Free temporary buffer */ - H5MM_xfree(tmp_buf); - } /* end if */ - - /* Free the memory used for the attribute */ - H5A_close(attr); - ret_value=SUCCEED; - - FUNC_LEAVE(ret_value); + /* Decrement references to that atom (and close it) */ + H5I_dec_ref (attr_id); + FUNC_LEAVE(SUCCEED); } /* H5Aclose() */ @@ -1320,6 +1312,25 @@ H5A_close(H5A_t *attr) assert(attr); + /* Check if the attribute has any data yet, if not, fill with zeroes */ + if(attr->ent_opened && !attr->initialized) { + uint8 *tmp_buf=H5MM_xcalloc(1,attr->data_size); + + if (NULL == tmp_buf) { + HRETURN_ERROR(H5E_ATTR, H5E_NOSPACE, FAIL, + "can't allocate attribute fill-value"); + } + + /* Go write the fill data to the attribute */ + if (H5A_write(attr,attr->dt,tmp_buf)<0) { + HRETURN_ERROR(H5E_ATTR, H5E_WRITEERROR, FAIL, + "can't write attribute"); + } + + /* Free temporary buffer */ + H5MM_xfree(tmp_buf); + } /* end if */ + /* Free dynamicly allocated items */ if(attr->name) H5MM_xfree(attr->name); diff --git a/src/H5Apublic.h b/src/H5Apublic.h index 71322dc..bf62290 100644 --- a/src/H5Apublic.h +++ b/src/H5Apublic.h @@ -17,7 +17,7 @@ #define _H5Apublic_H /* Public headers needed by this file */ - +#include <H5Ipublic.h> #ifdef __cplusplus extern "C" { @@ -153,9 +153,9 @@ H5F_init_interface(void) H5F_access_dflt.u.mpio.comm = MPI_COMM_SELF; H5F_access_dflt.u.mpio.info = MPI_INFO_NULL; #elif (H5F_LOW_DFLT == H5F_LOW_SPLIT) - /* Nothing to initialize */ +# error "H5F_LOW_SPLIT cannot be a default file driver" #elif (H5F_LOW_DFLT == H5F_LOW_FAMILY) - H5F_access_dflt.u.fam.offset_bits = 26u; /*64MB members*/ +# error "H5F_LOW_FAMILY cannot be a default file driver" #else # error "Unknown default file driver" #endif diff --git a/src/H5Ffamily.c b/src/H5Ffamily.c index d20a380..10572ce 100644 --- a/src/H5Ffamily.c +++ b/src/H5Ffamily.c @@ -100,16 +100,8 @@ H5F_fam_open(const char *name, const H5F_access_t *access_parms, assert (access_parms); assert (H5F_LOW_FAMILY==access_parms->driver); - - /* - * Use the default file driver or the specified driver for each of the - * family members. - */ - if (access_parms->u.fam.memb_access) { - memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); - } else { - memb_type = H5F_low_class (H5F_LOW_DFLT); - } + assert (access_parms->u.fam.memb_access); + memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); /* * If we're truncating the file then delete all but the first family @@ -386,14 +378,10 @@ H5F_fam_write(H5F_low_t *lf, const H5F_access_t *access_parms, assert(buf); assert (access_parms); assert (H5F_LOW_FAMILY==access_parms->driver); + assert (access_parms->u.fam.memb_access); /* Get the member driver */ - if (access_parms->u.fam.memb_access) { - memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); - } else { - memb_type = H5F_low_class (H5F_LOW_DFLT); - } - + memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); member_size = (hsize_t) 1 << lf->u.fam.offset_bits; membno = H5F_FAM_MEMBNO(addr, lf->u.fam.offset_bits); offset = H5F_FAM_OFFSET(addr, lf->u.fam.offset_bits); @@ -564,13 +552,10 @@ H5F_fam_access(const char *name, const H5F_access_t *access_parms, assert (name && *name); assert (access_parms); assert (H5F_LOW_FAMILY==access_parms->driver); + assert (access_parms->u.fam.memb_access); /* Get the driver for the family members */ - if (access_parms->u.fam.memb_access) { - memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); - } else { - memb_type = H5F_low_class (H5F_LOW_DFLT); - } + memb_type = H5F_low_class (access_parms->u.fam.memb_access->driver); /* Access the members */ for (membno=0; /*void*/; membno++) { diff --git a/src/H5Fsplit.c b/src/H5Fsplit.c new file mode 100644 index 0000000..1359816 --- /dev/null +++ b/src/H5Fsplit.c @@ -0,0 +1,443 @@ +/* + * Copyright (C) 1997 NCSA + * All rights reserved. + * + * Programmer: Robb Matzke <matzke@llnl.gov> + * Thursday, November 13, 1997 + * + * Purpose: A driver that splits the meta data and raw data into two + * separate files. The high-order bit of the file address + * determines whether the address refers to the meta data file + * (high order bit is clear) or the raw data file (high order bit + * is set). + */ +#include <H5private.h> +#include <H5Eprivate.h> +#include <H5Fprivate.h> +#include <H5MFprivate.h> +#include <H5MMprivate.h> + +/* Default file name extensions */ +#define H5F_SPLIT_META_EXT ".meta" +#define H5F_SPLIT_RAW_EXT ".raw" + +#define PABLO_MASK H5F_split +static hbool_t interface_initialize_g = FALSE; +#define INTERFACE_INIT NULL + +static hbool_t H5F_split_access(const char *name, + const H5F_access_t *access_parms, int mode, + H5F_search_t *key/*out*/); +static H5F_low_t *H5F_split_open(const char *name, + const H5F_access_t *access_parms, uintn flags, + H5F_search_t *key/*out*/); +static herr_t H5F_split_close(H5F_low_t *lf, const H5F_access_t *access_parms); +static herr_t H5F_split_read(H5F_low_t *lf, const H5F_access_t *access_parms, + const haddr_t *addr, size_t size, + uint8 *buf/*out*/); +static herr_t H5F_split_write(H5F_low_t *lf, const H5F_access_t *access_parms, + const haddr_t *addr, size_t size, + const uint8 *buf); +static herr_t H5F_split_flush(H5F_low_t *lf, const H5F_access_t *access_parms); +static herr_t H5F_split_extend(H5F_low_t *lf, const H5F_access_t *access_parms, + intn op, hsize_t size, haddr_t *addr/*out*/); + +const H5F_low_class_t H5F_LOW_SPLIT_g[1] = {{ + H5F_split_access, /* access method */ + H5F_split_open, /* open method */ + H5F_split_close, /* close method */ + H5F_split_read, /* read method */ + H5F_split_write, /* write method */ + H5F_split_flush, /* flush method */ + H5F_split_extend, /* extend method */ +}}; + +/* + * This is the bit that determines whether the address is part of the meta + * data file or part of the raw data file. Eventually we'll want to pass + * this kind of thing down to this function from above... + */ +#define H5F_SPLIT_MASK 0x80000000 + + +/*------------------------------------------------------------------------- + * Function: H5F_split_open + * + * Purpose: Opens a split meta data/raw data family with the specified + * base name. The name of the meta data file will be created by + * appending `.h5' while the name of the raw data file will be + * created by appending `.raw'. + * + * Return: Success: Low-level file pointer + * + * Failure: NULL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static H5F_low_t * +H5F_split_open(const char *name, const H5F_access_t *access_parms, + uintn flags, H5F_search_t *key/*out*/) +{ + H5F_low_t *lf = NULL, *ret_value = NULL; + char fullname[4096]; + const char *ext; /*file name extension*/ + const H5F_low_class_t *meta_type = NULL; + const H5F_low_class_t *raw_type = NULL; + + FUNC_ENTER(H5F_split_open, NULL); + + assert(name && *name); + assert (access_parms); + assert (H5F_LOW_SPLIT==access_parms->driver); + assert (access_parms->u.split.meta_access); + assert (access_parms->u.split.raw_access); + + /* Get member types */ + meta_type = H5F_low_class (access_parms->u.split.meta_access->driver); + raw_type = H5F_low_class (access_parms->u.split.raw_access->driver); + + /* Create the file descriptor */ + lf = H5MM_xcalloc(1, sizeof(H5F_low_t)); + lf->u.split.name = H5MM_xstrdup(name); + lf->u.split.mask = H5F_SPLIT_MASK; + + /* Open the meta data file */ + ext = access_parms->u.split.meta_ext ? + access_parms->u.split.meta_ext : H5F_SPLIT_META_EXT; + if (strlen (name)+strlen (ext) >= sizeof fullname) { + HGOTO_ERROR (H5E_IO, H5E_CANTINIT, NULL, "file name is too long"); + } + strcpy (fullname, name); + strcat (fullname, ext); + + lf->u.split.meta = H5F_low_open(meta_type, fullname, + access_parms->u.split.meta_access, + flags, key/*out*/); + if (NULL == lf->u.split.meta) { + HGOTO_ERROR(H5E_IO, H5E_CANTOPENFILE, NULL, "can't open meta file"); + } + + /* Open the raw data file */ + ext = access_parms->u.split.raw_ext ? + access_parms->u.split.raw_ext : H5F_SPLIT_RAW_EXT; + if (strlen (name)+strlen (ext) >= sizeof fullname) { + HGOTO_ERROR (H5E_IO, H5E_CANTINIT, NULL, "file name is too long"); + } + strcpy (fullname, name); + strcat (fullname, ext); + + lf->u.split.raw = H5F_low_open(raw_type, fullname, + access_parms->u.split.raw_access, + flags, NULL); + if (NULL == lf->u.split.raw) { + HGOTO_ERROR(H5E_IO, H5E_CANTOPENFILE, NULL, "can't open raw file"); + } + + /* Initialize the file size */ + H5F_low_size(lf->u.split.raw, &(lf->eof)); + lf->eof.offset |= lf->u.split.mask; + + HRETURN(lf); + + done: + if (!ret_value) { + if (lf) { + H5F_split_close(lf, access_parms); + H5MM_xfree(lf); + } + } + FUNC_LEAVE(ret_value); +} + +/*------------------------------------------------------------------------- + * Function: H5F_split_close + * + * Purpose: Closes a split file. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_split_close(H5F_low_t *lf, const H5F_access_t *access_parms) +{ + FUNC_ENTER(H5F_split_close, FAIL); + + assert(lf); + + H5F_low_close(lf->u.split.meta, access_parms->u.split.meta_access); + H5F_low_close(lf->u.split.raw, access_parms->u.split.raw_access); + H5MM_xfree(lf->u.split.name); + + FUNC_LEAVE(SUCCEED); +} + +/*------------------------------------------------------------------------- + * Function: H5F_split_read + * + * Purpose: Reads a chunk of contiguous data from a split file. We + * assume that the data being read never crosses the meta + * data/raw data boundary. Reading past the end of a file + * returns zeros instead of failing. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_split_read(H5F_low_t *lf, const H5F_access_t *access_parms, + const haddr_t *addr, size_t size, uint8 *buf/*out*/) +{ + haddr_t tmp_addr; + H5F_low_t *sub = NULL; + herr_t status; + const H5F_access_t *sub_parms = NULL; + + FUNC_ENTER(H5F_split_read, FAIL); + + assert(lf); + assert(addr && H5F_addr_defined(addr)); + assert(buf); + + /* Which file to we actually read from? */ + if (addr->offset & lf->u.split.mask) { + sub = lf->u.split.raw; + sub_parms = access_parms->u.split.raw_access; + tmp_addr.offset = addr->offset & (lf->u.split.mask - 1); + } else { + sub = lf->u.split.meta; + sub_parms = access_parms->u.split.meta_access; + tmp_addr = *addr; + } + + /* Read the data */ + status = H5F_low_read(sub, sub_parms, &tmp_addr, size, buf/*out*/); + FUNC_LEAVE(status); +} + + +/*------------------------------------------------------------------------- + * Function: H5F_split_write + * + * Purpose: Writes BUF to either the meta data file or the raw data file. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_split_write(H5F_low_t *lf, const H5F_access_t *access_parms, + const haddr_t *addr, size_t size, const uint8 *buf) +{ + haddr_t tmp_addr; + H5F_low_t *sub = NULL; + herr_t status; + const H5F_access_t *sub_parms = NULL; + + FUNC_ENTER(H5F_split_write, FAIL); + + assert(lf); + assert(addr && H5F_addr_defined(addr)); + assert(buf); + + /* Which file to we actually write to? */ + if (addr->offset & lf->u.split.mask) { + sub = lf->u.split.raw; + sub_parms = access_parms->u.split.raw_access; + tmp_addr.offset = addr->offset & (lf->u.split.mask - 1); + } else { + sub = lf->u.split.meta; + sub_parms = access_parms->u.split.meta_access; + tmp_addr = *addr; + } + + /* Write the data */ + status = H5F_low_write(sub, sub_parms, &tmp_addr, size, buf); + FUNC_LEAVE(status); +} + +/*------------------------------------------------------------------------- + * Function: H5F_split_flush + * + * Purpose: Flushes all data to disk. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_split_flush(H5F_low_t *lf, const H5F_access_t *access_parms) +{ + herr_t ret_value = SUCCEED; + + FUNC_ENTER(H5F_split_flush, FAIL); + + assert(lf); + + ret_value = (H5F_low_flush(lf->u.split.meta, + access_parms->u.split.meta_access) >= 0 && + H5F_low_flush(lf->u.split.raw, + access_parms->u.split.raw_access) >= 0); + + FUNC_LEAVE(ret_value); +} + +/*------------------------------------------------------------------------- + * Function: H5F_split_access + * + * Purpose: Determines if both members of the split data file family can + * be accessed and returns the key for the first member of the + * family. + * + * Return: Success: TRUE or FALSE + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Monday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static hbool_t +H5F_split_access(const char *name, const H5F_access_t *access_parms, + int mode, H5F_search_t *key/*out*/) +{ + char fullname[4096]; + hbool_t status; + const char *ext; /*file extension*/ + const H5F_low_class_t *meta_type = NULL; + const H5F_low_class_t *raw_type = NULL; + + FUNC_ENTER(H5F_split_access, FAIL); + + assert(name && *name); + assert (access_parms); + assert (H5F_LOW_SPLIT==access_parms->driver); + assert (access_parms->u.split.meta_access); + assert (access_parms->u.split.raw_access); + + /* The meta data member */ + meta_type = H5F_low_class (access_parms->u.split.meta_access->driver); + ext = access_parms->u.split.meta_ext ? + access_parms->u.split.meta_ext : H5F_SPLIT_META_EXT; + if (strlen (name)+strlen (ext) >= sizeof fullname) { + HRETURN_ERROR (H5E_IO, H5E_CANTINIT, FAIL, "file name is too long"); + } + strcpy (fullname, name); + strcat (fullname, ext); + + status = H5F_low_access(meta_type, fullname, + access_parms->u.split.meta_access, + mode, key/*out*/); + if (status < 0) { + HRETURN_ERROR(H5E_IO, H5E_CANTINIT, FAIL, + "access call failed for meta data member"); + } + if (!status) HRETURN(FALSE); + + /* The raw data member */ + raw_type = H5F_low_class (access_parms->u.split.raw_access->driver); + ext = access_parms->u.split.raw_ext ? + access_parms->u.split.raw_ext : H5F_SPLIT_RAW_EXT; + if (strlen (name)+strlen (ext) >= sizeof fullname) { + HRETURN_ERROR (H5E_IO, H5E_CANTINIT, FAIL, "file name is too long"); + } + strcpy (fullname, name); + strcat (fullname, ext); + + status = H5F_low_access(raw_type, fullname, + access_parms->u.split.raw_access, + mode, NULL/*out*/); + if (status < 0) { + HRETURN_ERROR(H5E_IO, H5E_CANTINIT, FAIL, + "access call failed for raw data member"); + } + FUNC_LEAVE(status); +} + +/*------------------------------------------------------------------------- + * Function: H5F_split_extend + * + * Purpose: Allocates memory from the end of the meta data file or raw + * data file. + * + * Return: Success: SUCCEED with the address of the allocated + * memory returned through the ADDR argument. + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * Thursday, November 13, 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_split_extend(H5F_low_t *lf, const H5F_access_t *access_parms, intn op, + hsize_t size, haddr_t *addr/*out*/) +{ + FUNC_ENTER(H5F_split_extend, FAIL); + + assert(lf); + assert(H5MF_META == op || H5MF_RAW == op); + assert(size > 0); + assert(addr); + + if (H5MF_META == op) { + if (H5F_low_extend(lf->u.split.meta, access_parms->u.split.meta_access, + op, size, addr/*out*/)<0) { + HRETURN_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, + "meta data allocation failed"); + } + if (addr->offset + size > lf->eof.offset) { + lf->eof.offset = addr->offset + size; + } + } else { + if (H5F_low_extend(lf->u.split.raw, access_parms->u.split.raw_access, + op, size, addr/*out*/)<0) { + HRETURN_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, + "raw data allocation failed"); + } + addr->offset |= lf->u.split.mask; + lf->eof = lf->u.split.raw->eof; + lf->eof.offset |= lf->u.split.mask; + } + + FUNC_LEAVE(SUCCEED); +} @@ -58,7 +58,6 @@ static char RcsId[] = "@(#)$Revision$"; 1/7/96 - Finished coding prototype 6/10/97 - Moved into HDF5 library */ - #include <H5private.h> #include <H5Iprivate.h> #include <H5Eprivate.h> @@ -786,7 +786,11 @@ H5O_count (H5G_entry_t *ent, const H5O_class_t *type) * the null pointer, then this function will malloc() memory * to hold the result and return its pointer instead. * - * Return: Success: Ptr to message in native format. + * Return: Success: Ptr to message in native format. The message + * should be freed by calling H5O_reset(). If + * MESG is a null pointer then the caller should + * also call H5MM_xfree() on the return value + * after calling H5O_reset(). * * Failure: NULL * @@ -1449,8 +1449,8 @@ H5Pset_split (hid_t tid, const char *meta_ext, hid_t meta_tid, const char *raw_ext, hid_t raw_tid) { H5F_access_t *tmpl = NULL; - H5F_access_t *meta_tmpl = NULL; - H5F_access_t *raw_tmpl = NULL; + H5F_access_t *meta_tmpl = &H5F_access_dflt; + H5F_access_t *raw_tmpl = &H5F_access_dflt; FUNC_ENTER (H5Pset_split, FAIL); @@ -1462,13 +1462,13 @@ H5Pset_split (hid_t tid, const char *meta_ext, hid_t meta_tid, } if (H5P_DEFAULT!=meta_tid && (H5P_FILE_ACCESS != H5Pget_class(meta_tid) || - NULL == (tmpl = H5I_object(meta_tid)))) { + NULL == (meta_tmpl = H5I_object(meta_tid)))) { HRETURN_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a file access template"); } if (H5P_DEFAULT!=raw_tid && (H5P_FILE_ACCESS != H5Pget_class(raw_tid) || - NULL == (tmpl = H5I_object(raw_tid)))) { + NULL == (raw_tmpl = H5I_object(raw_tid)))) { HRETURN_ERROR(H5E_ARGS, H5E_BADTYPE, FAIL, "not a file access template"); } @@ -1498,11 +1498,8 @@ H5Pset_split (hid_t tid, const char *meta_ext, hid_t meta_tid, * if META_PROPERTIES and/or RAW_PROPERTIES are non-null then * the file access property list of the meta file and/or raw * file is copied and its OID returned through these arguments. - * If the meta file or raw file has no property list then an OID - * of FAIL (-1) is returned but the H5Pget_split() function - * still returns SUCCEED. In the future, additional arguments - * may be added to this function to match those added to - * H5Pset_sec2(). + * In the future, additional arguments may be added to this + * function to match those added to H5Pset_sec2(). * * Return: Success: SUCCEED * @@ -1556,18 +1553,19 @@ H5Pget_split (hid_t tid, size_t meta_ext_size, char *meta_ext/*out*/, strncpy (raw_ext, ".raw", raw_ext_size); } } - if (meta_properties && tmpl->u.split.meta_access) { + if (meta_properties) { + assert (tmpl->u.split.meta_access); *meta_properties = H5P_create (H5P_FILE_ACCESS, H5P_copy (H5P_FILE_ACCESS, tmpl->u.split.meta_access)); } - if (raw_properties && tmpl->u.split.raw_access) { + if (raw_properties) { + assert (tmpl->u.split.raw_access); *raw_properties = H5P_create (H5P_FILE_ACCESS, H5P_copy (H5P_FILE_ACCESS, tmpl->u.split.raw_access)); } - FUNC_LEAVE (SUCCEED); } @@ -1629,12 +1627,9 @@ H5Pset_family (hid_t tid, size_t offset_bits, hid_t memb_tid) * Purpose: If the file access property list is set to the family driver * then this function returns zero; otherwise it returns a * negative value. On success, if MEMB_TID is a non-null - * pointer it will be initialized with the OID of a copy of the - * file access template used for the family members. If the - * family members have no file access template (that is, they - * are using the default values) then FAIL (-1) is returned for - * the member property list OID but the function still returns - * SUCCEED. In the future, additional arguments may be added to + * pointer it will be initialized with the id of an open + * property list: the file access property list for the family + * members. In the future, additional arguments may be added to * this function to match those added to H5Pset_family(). * * Return: Success: SUCCEED @@ -1667,12 +1662,11 @@ H5Pget_family (hid_t tid, size_t *offset_bits/*out*/, hid_t *memb_tid/*out*/) } /* Output args */ - if (memb_tid && tmpl->u.fam.memb_access) { + if (memb_tid) { + assert (tmpl->u.fam.memb_access); *memb_tid = H5P_create (H5P_FILE_ACCESS, H5P_copy (H5P_FILE_ACCESS, tmpl->u.fam.memb_access)); - } else if (memb_tid) { - *memb_tid = FAIL; } if (offset_bits) *offset_bits = tmpl->u.fam.offset_bits; @@ -250,6 +250,34 @@ H5T_init_interface(void) FUNC_LEAVE(ret_value); } + +/*------------------------------------------------------------------------- + * Function: H5T_unlock_cb + * + * Purpose: Clear the locked flag for a data type. This function is + * called when the library is closing in order to unlock all + * registered data types and thus make them free-able. + * + * Return: Success: 0 + * + * Failure: 0 + * + * Programmer: Robb Matzke + * Monday, April 27, 1998 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static intn +H5T_unlock_cb (void *dt, const void __unused__ *key) +{ + FUNC_ENTER (H5T_unlock_cb, FAIL); + assert (dt); + ((H5T_t*)dt)->locked = FALSE; + FUNC_LEAVE (0); +} + /*-------------------------------------------------------------------------- NAME H5T_term_interface @@ -333,33 +361,9 @@ H5T_term_interface(void) (cfunc)(FAIL, FAIL, pcdata, 0, NULL, NULL); } + /* Unlock all datatypes, then free them */ + H5I_search (H5_DATATYPE, H5T_unlock_cb, NULL); H5I_destroy_group(H5_DATATYPE); - H5T_NATIVE_CHAR_g = FAIL; - H5T_NATIVE_UCHAR_g = FAIL; - H5T_NATIVE_SHORT_g = FAIL; - H5T_NATIVE_USHORT_g = FAIL; - H5T_NATIVE_INT_g = FAIL; - H5T_NATIVE_UINT_g = FAIL; - H5T_NATIVE_LONG_g = FAIL; - H5T_NATIVE_LLONG_g = FAIL; - H5T_NATIVE_ULLONG_g = FAIL; - H5T_NATIVE_HYPER_g = FAIL; - H5T_NATIVE_UHYPER_g = FAIL; - H5T_NATIVE_INT8_g = FAIL; - H5T_NATIVE_UINT8_g = FAIL; - H5T_NATIVE_INT16_g = FAIL; - H5T_NATIVE_UINT16_g = FAIL; - H5T_NATIVE_INT32_g = FAIL; - H5T_NATIVE_UINT32_g = FAIL; - H5T_NATIVE_INT64_g = FAIL; - H5T_NATIVE_UINT64_g = FAIL; - H5T_NATIVE_ULONG_g = FAIL; - H5T_NATIVE_FLOAT_g = FAIL; - H5T_NATIVE_DOUBLE_g = FAIL; - H5T_NATIVE_TIME_g = FAIL; - H5T_NATIVE_STRING_g = FAIL; - H5T_NATIVE_BITFIELD_g = FAIL; - H5T_NATIVE_OPAQUE_g = FAIL; } @@ -2765,6 +2769,7 @@ H5T_close(H5T_t *dt) if (dt && H5T_COMPOUND == dt->type) { for (i = 0; i < dt->u.compnd.nmembs; i++) { H5MM_xfree(dt->u.compnd.memb[i].name); + H5T_close (dt->u.compnd.memb[i].type); } H5MM_xfree(dt->u.compnd.memb); H5MM_xfree(dt); |