From cbf1f8dbb5bebca21959d0eb8bb93100648b8c95 Mon Sep 17 00:00:00 2001 From: Robb Matzke Date: Fri, 29 Aug 1997 17:23:04 -0500 Subject: [svn-r55] ./src/H5F.c Added H5Fflush() and H5F_flush() which flush (and optionally invalidate the cache) and flush the file boot block. H5Fcreate() calls H5F_flush() to output the boot block. H5Fclose() calls H5F_flush() to update the boot block. H5F_debug() prints the root symbol table entry. ./src/H5Fpublic.h Added H5Fflush() prototype. ./src/H5G.c The name message is removed when an object moves from the root object position into a directory. Added H5G_debug() to print a symbol table entry. Most of the code was just moved from H5G_node_debug(). ./src/H5Gnode.c Moved some debugging code into H5G_debug(). ./src/H5Gprivate.c Added H5G_debug() prototype. ./src/H5O.c Implemented H5O_remove(). Added identifiers for H5O_SIM_DIM and H5O_SIM_DTYPE so they can be read from files. H5O_load() combines adjacent null messages for better memory management. ./src/H5Oprivate.h Changed minimum header data block size from 16 to 32 bytes. Changed prototype for H5O_remove() --- src/H5F.c | 167 +++++++++++++++++++++++++++++++++++++++++-------------- src/H5Fpublic.h | 1 + src/H5G.c | 90 +++++++++++++++++++++++++++++- src/H5Gnode.c | 54 +----------------- src/H5Gprivate.h | 2 + src/H5O.c | 108 +++++++++++++++++++++++++++-------- src/H5Oprivate.h | 5 +- 7 files changed, 304 insertions(+), 123 deletions(-) diff --git a/src/H5F.c b/src/H5F.c index 3d8b570..3b08963 100644 --- a/src/H5F.c +++ b/src/H5F.c @@ -53,6 +53,7 @@ static intn interface_initialize_g = FALSE; static herr_t H5F_init_interface(void); static hdf5_file_t *H5F_new (void); static hdf5_file_t *H5F_dest (hdf5_file_t *f); +static herr_t H5F_flush (hdf5_file_t *f, hbool_t invalidate); /*-------------------------------------------------------------------------- NAME @@ -415,13 +416,15 @@ H5F_dest (hdf5_file_t *f) Robb Matzke, 18 Jul 1997 File struct creation and destruction is through H5F_new() H5F_dest(). Writing the root symbol table entry is done with H5G_encode(). + + Robb Matzke, 29 Aug 1997 + Moved creation of the boot block to H5F_flush(). --------------------------------------------------------------------------*/ hatom_t H5Fcreate(const char *filename, uintn flags, hatom_t create_temp, hatom_t access_temp) { hdf5_file_t *new_file=NULL; /* file struct for new file */ hdf_file_t f_handle=H5F_INVALID_FILE; /* file handle */ const file_create_temp_t *f_create_parms; /* pointer to the parameters to use when creating the file */ - uint8 temp_buf[H5F_BOOTBLOCK_SIZE], *p; /* temporary buffer for encoding header */ intn file_exists=0; /* flag to indicate that file exists already */ hatom_t ret_value = FAIL; @@ -485,46 +488,10 @@ hatom_t H5Fcreate(const char *filename, uintn flags, hatom_t create_temp, hatom_ HDmemcpy(&new_file->file_access_parms,f_access_parms,sizeof(file_access_temp_t)); #endif /* LATER */ - /* Create the basic skeleton of the file */ - - /* Seek to the correct offset to write out the file signature & boot-block */ - if(new_file->file_create_parms.userblock_size>0) - if(H5F_SEEK(new_file->file_handle,new_file->file_create_parms.userblock_size)==FAIL) - HGOTO_ERROR(H5E_IO, H5E_SEEKERROR, FAIL); - - /* Write out the file-signature */ - if(H5F_WRITE(new_file->file_handle,H5F_SIGNATURE,H5F_SIGNATURE_LEN)==FAIL) - HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL); - - /* Encode the boot block */ - p=temp_buf; - *p++=f_create_parms->bootblock_ver; /* Encode Boot-block version # */ - *p++=f_create_parms->smallobject_ver; /* Encode Small-Object Heap version # */ - *p++=f_create_parms->freespace_ver; /* Encode Free-Space Info version # */ - *p++=f_create_parms->objectdir_ver; /* Encode Object Directory Format version # */ - *p++=f_create_parms->sharedheader_ver; /* Encode Shared-Header Info version # */ - *p++=f_create_parms->offset_size; /* Encode the number of bytes for the offset */ - *p++=f_create_parms->length_size; /* Encode the number of bytes for the length */ - *p++=0; /* Encode the reserved byte :-) */ - UINT16ENCODE(p,f_create_parms->sym_leaf_k); /*symbol table leaf node 1/2 rank */ - UINT16ENCODE(p,f_create_parms->btree_k[H5B_SNODE_ID]);/*stab internal node 1/2 rank */ - UINT32ENCODE(p,new_file->consist_flags); /* Encode File-Consistancy flags */ - H5F_encode_offset(new_file,p,new_file->smallobj_off); /* Encode offset of global small-object heap */ - H5F_encode_offset(new_file,p,new_file->freespace_off); /* Encode offset of global free-space heap */ - /* Predict the header length and encode it: */ - H5F_encode_length(new_file,p,((p-temp_buf) + - H5F_SIZEOF_SIZE(new_file) + - H5G_SIZEOF_ENTRY(new_file))); - - /* Encode the uninitialized root symbol-table entry, by adding it to the boot block */ - if (H5G_encode (new_file, &p, new_file->root_sym)<0) - HGOTO_ERROR (H5E_IO, H5E_WRITEERROR, FAIL); - - /* Write out the boot block */ - if(H5F_WRITE(new_file->file_handle,temp_buf,(size_t)(p-temp_buf))==FAIL) - HGOTO_ERROR(H5E_IO, H5E_WRITEERROR, FAIL); - new_file->logical_len = p - temp_buf; - + /* Flush the file signature and boot block */ + if (H5F_flush (new_file, FALSE)<0) { + HGOTO_ERROR (H5E_IO, H5E_CANTINIT, FAIL); /*can't write file boot block*/ + } /* Get an atom for the file */ if((ret_value=H5Aregister_atom(H5_FILE, new_file))==FAIL) @@ -735,6 +702,115 @@ done: /*-------------------------------------------------------------------------- NAME + H5Fflush + PURPOSE + Flush all cached data to disk and optionally invalidates all cached + data. + USAGE + herr_t H5Fclose(fid, invalidate) + hatom_t fid; IN: File ID of file to close. + hbool_t invalidate; IN: Invalidate all of the cache? + RETURNS + SUCCEED/FAIL + DESCRIPTION + This function flushes all cached data to disk and, if INVALIDATE + is non-zero, removes cached objects from the cache so they must be + re-read from the file on the next access to the object. + + MODIFICATIONS: +--------------------------------------------------------------------------*/ +herr_t +H5Fflush (hatom_t fid, hbool_t invalidate) +{ + hdf5_file_t *file = NULL; + + FUNC_ENTER (H5Fflush, H5F_init_interface, FAIL); + H5ECLEAR; + + /* check arguments */ + if (H5_FILE!=H5Aatom_group (fid)) { + HRETURN_ERROR (H5E_ARGS, H5E_BADTYPE, FAIL); /*not a file atom*/ + } + if (NULL==(file=H5Aatom_object (fid))) { + HRETURN_ERROR (H5E_ATOM, H5E_BADATOM, FAIL); /*can't get file struct*/ + } + + /* do work */ + if (H5F_flush (file, invalidate)<0) { + HRETURN_ERROR (H5E_CACHE, H5E_CANTFLUSH, FAIL); /*flush failed*/ + } + + FUNC_LEAVE (SUCCEED); +} + + +/*------------------------------------------------------------------------- + * Function: H5F_flush + * + * Purpose: Flushes (and optionally invalidates) cached data plus the + * file boot block. If the logical file size field is zero + * then it is updated to be the length of the boot block. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * robb@maya.nuance.com + * Aug 29 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +static herr_t +H5F_flush (hdf5_file_t *f, hbool_t invalidate) +{ + uint8 buf[2048], *p=buf; + + FUNC_ENTER (H5F_flush, H5F_init_interface, FAIL); + + /* nothing to do if the file is read only */ + if (0==(H5ACC_WRITE & f->acc_perm)) HRETURN (SUCCEED); + + /* flush (and invalidate) the entire cache */ + if (H5AC_flush (f, NULL, 0, invalidate)<0) { + HRETURN_ERROR (H5E_CACHE, H5E_CANTFLUSH, FAIL); /*can't flush cache*/ + } + + /* encode the file boot block */ + HDmemcpy (p, H5F_SIGNATURE, H5F_SIGNATURE_LEN); + p += H5F_SIGNATURE_LEN; + + *p++ = f->file_create_parms.bootblock_ver; + *p++ = f->file_create_parms.smallobject_ver; + *p++ = f->file_create_parms.freespace_ver; + *p++ = f->file_create_parms.objectdir_ver; + *p++ = f->file_create_parms.sharedheader_ver; + *p++ = H5F_SIZEOF_OFFSET (f); + *p++ = H5F_SIZEOF_SIZE (f); + *p++ = 0; /*reserved*/ + UINT16ENCODE (p, f->file_create_parms.sym_leaf_k); + UINT16ENCODE (p, f->file_create_parms.btree_k[H5B_SNODE_ID]); + UINT32ENCODE (p, f->consist_flags); + H5F_encode_offset (f, p, f->smallobj_off); + H5F_encode_offset (f, p, f->freespace_off); + H5F_encode_length (f, p, f->logical_len); + H5G_encode (f, &p, f->root_sym); + + /* write the boot block to disk */ + if (H5F_block_write (f, 0, p-buf, buf)<0) { + HRETURN_ERROR (H5E_IO, H5E_WRITEERROR, FAIL); /*can't write header*/ + } + + /* update file length if necessary */ + if (f->logical_len<=0) f->logical_len = p-buf; + + FUNC_LEAVE (SUCCEED); +} + +/*-------------------------------------------------------------------------- + NAME H5Fclose PURPOSE Close an open HDF5 file. @@ -751,6 +827,10 @@ done: MODIFICATIONS: Robb Matzke, 18 Jul 1997 File struct destruction is through H5F_dest(). + + Robb Matzke, 29 Aug 1997 + The file boot block is flushed to disk since it's contents may have + changed. --------------------------------------------------------------------------*/ herr_t H5Fclose(hatom_t fid) { @@ -771,8 +851,8 @@ herr_t H5Fclose(hatom_t fid) /* Decrement the ref. count and recycle the file structure */ if((--file->ref_count)==0) { - H5AC_flush (file, NULL, 0, TRUE); if(file->file_handle!=H5F_INVALID_FILE) { + H5F_flush (file, TRUE); H5F_CLOSE(file->file_handle); } H5F_dest (file); @@ -955,6 +1035,9 @@ H5F_debug (hdf5_file_t *f, haddr_t addr, FILE *stream, intn indent, fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, "Shared header version number:", (unsigned)(f->file_create_parms.sharedheader_ver)); + + fprintf (stream, "%*sRoot symbol table entry:\n", indent, ""); + H5G_debug (f, f->root_sym, stream, indent+3, MAX(0, fwidth-3)); FUNC_LEAVE (SUCCEED); } diff --git a/src/H5Fpublic.h b/src/H5Fpublic.h index b5e3350..84bb359 100644 --- a/src/H5Fpublic.h +++ b/src/H5Fpublic.h @@ -36,6 +36,7 @@ hbool_t H5Fis_hdf5(const char *filename); hatom_t H5Fcreate(const char *filename, uintn flags, hatom_t create_template, hatom_t access_template); hatom_t H5Fopen(const char *filename, uintn flags, hatom_t access_template); herr_t H5Fclose(hatom_t fid); +herr_t H5Fflush (hatom_t fid, hbool_t invalidate); hatom_t H5Fget_create_template(hatom_t fid); #ifdef __cplusplus diff --git a/src/H5G.c b/src/H5G.c index b1441c6..3e756b5 100644 --- a/src/H5G.c +++ b/src/H5G.c @@ -327,12 +327,17 @@ H5G_mkroot (hdf5_file_t *f, size_t size_hint) if (H5O_read (f, f->root_sym->header, f->root_sym, H5O_STAB, 0, &stab)) { /* root directory already exists */ HRETURN_ERROR (H5E_DIRECTORY, H5E_EXISTS, FAIL); + } else if (H5O_read (f, f->root_sym->header, f->root_sym, H5O_NAME, 0, &name)) { - root = *(f->root_sym); - root_name = name.s; /*dont reset name until root_name is done*/ + /*dont reset name until root_name is done*/ + root_name = name.s; reset = TRUE; - H5O_remove (f, f->root_sym->header, f->root_sym, H5O_NAME, H5O_ALL); + + /* remove all name messages -- don't care if it fails */ + root = *(f->root_sym); + H5O_remove (f, root.header, &root, NULL, H5O_NAME, H5O_ALL); + } else { root = *(f->root_sym); root_name = "Root Object"; @@ -1260,4 +1265,83 @@ H5G_encode (hdf5_file_t *f, uint8 **pp, H5G_entry_t *ent) FUNC_LEAVE (SUCCEED); } + +/*------------------------------------------------------------------------- + * Function: H5G_debug + * + * Purpose: Prints debugging information about a symbol table entry. + * + * Return: Success: SUCCEED + * + * Failure: FAIL + * + * Programmer: Robb Matzke + * robb@maya.nuance.com + * Aug 29 1997 + * + * Modifications: + * + *------------------------------------------------------------------------- + */ +herr_t +H5G_debug (hdf5_file_t *f, H5G_entry_t *ent, FILE *stream, intn indent, + intn fwidth) +{ + int i; + char buf[64]; + + FUNC_ENTER (H5G_debug, NULL, FAIL); + + fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, + "Name offset into private heap:", + (unsigned long)(ent->name_off)); + fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, + "Object header address:", + (unsigned long)(ent->header)); + + fprintf (stream, "%*s%-*s ", indent, "", fwidth, + "Symbol type:"); + switch (ent->type) { + case H5G_NOTHING_CACHED: + fprintf (stream, "Nothing Cached\n"); + break; + + case H5G_CACHED_SDATA: + fprintf (stream, "S-data\n"); + fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, + "Number type length:", + (unsigned)(ent->cache.sdata.nt.length)); + fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, + "Number type architecture:", + (unsigned)(ent->cache.sdata.nt.arch)); + fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, + "Number type type:", + (unsigned)(ent->cache.sdata.nt.type)); + fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, + "Dimensionality:", + (unsigned)(ent->cache.sdata.ndim)); + for (i=0; icache.sdata.ndim && i<4; i++) { + sprintf (buf, "Dimension %d", i); + fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, + buf, + (unsigned)(ent->cache.sdata.dim[i])); + } + break; + + case H5G_CACHED_STAB: + fprintf (stream, "Symbol Table\n"); + fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, + "B-tree address:", + (unsigned long)(ent->cache.stab.btree)); + fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, + "Heap address:", + (unsigned long)(ent->cache.stab.heap)); + break; + + default: + fprintf (stream, "*** Unknown symbol type %d\n", ent->type); + break; + } + FUNC_LEAVE (SUCCEED); +} diff --git a/src/H5Gnode.c b/src/H5Gnode.c index dd3e832..6c0866b 100644 --- a/src/H5Gnode.c +++ b/src/H5Gnode.c @@ -863,8 +863,7 @@ herr_t H5G_node_debug (hdf5_file_t *f, haddr_t addr, FILE *stream, intn indent, intn fwidth, haddr_t heap) { - int i, j; - char buf[64]; + int i; H5G_node_t *sn = NULL; herr_t status; const char *s; @@ -909,56 +908,7 @@ H5G_node_debug (hdf5_file_t *f, haddr_t addr, FILE *stream, intn indent, "Name:", s); } - fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, - "Name offset into private heap:", - (unsigned long)(sn->entry[i].name_off)); - fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, - "Object header address:", - (unsigned long)(sn->entry[i].header)); - - fprintf (stream, "%*s%-*s ", indent, "", fwidth, - "Symbol type:"); - switch (sn->entry[i].type) { - case H5G_NOTHING_CACHED: - fprintf (stream, "Nothing Cached\n"); - break; - - case H5G_CACHED_SDATA: - fprintf (stream, "S-data\n"); - fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, - "Number type length:", - (unsigned)(sn->entry[i].cache.sdata.nt.length)); - fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, - "Number type architecture:", - (unsigned)(sn->entry[i].cache.sdata.nt.arch)); - fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, - "Number type type:", - (unsigned)(sn->entry[i].cache.sdata.nt.type)); - fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, - "Dimensionality:", - (unsigned)(sn->entry[i].cache.sdata.ndim)); - for (j=0; jentry[i].cache.sdata.ndim && j<4; j++) { - sprintf (buf, "Dimension %d", j); - fprintf (stream, "%*s%-*s %u\n", indent, "", fwidth, - buf, - (unsigned)(sn->entry[i].cache.sdata.dim[j])); - } - break; - - case H5G_CACHED_STAB: - fprintf (stream, "Symbol Table\n"); - fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, - "B-tree address:", - (unsigned long)(sn->entry[i].cache.stab.btree)); - fprintf (stream, "%*s%-*s %lu\n", indent, "", fwidth, - "Heap address:", - (unsigned long)(sn->entry[i].cache.stab.heap)); - break; - - default: - fprintf (stream, "*** Unknown symbol type %d\n", sn->entry[i].type); - break; - } + H5G_debug (f, sn->entry+i, stream, indent, fwidth); } FUNC_LEAVE (SUCCEED); diff --git a/src/H5Gprivate.h b/src/H5Gprivate.h index 945291e..744a525 100644 --- a/src/H5Gprivate.h +++ b/src/H5Gprivate.h @@ -170,6 +170,8 @@ herr_t H5G_decode (hdf5_file_t *f, uint8 **pp, H5G_entry_t *ent); herr_t H5G_decode_vec (hdf5_file_t *f, uint8 **pp, H5G_entry_t *ent, intn n); herr_t H5G_encode (hdf5_file_t *f, uint8 **pp, H5G_entry_t *ent); herr_t H5G_encode_vec (hdf5_file_t *f, uint8 **pp, H5G_entry_t *ent, intn n); +herr_t H5G_debug (hdf5_file_t *f, H5G_entry_t *ent, FILE *stream, intn indent, + intn fwidth); #endif diff --git a/src/H5O.c b/src/H5O.c index eaf860a..256393c 100644 --- a/src/H5O.c +++ b/src/H5O.c @@ -47,9 +47,9 @@ static intn interface_initialize_g = FALSE; /* ID to type mapping */ static const H5O_class_t *const message_type_g[] = { H5O_NULL, /*0x0000 Null */ - NULL, /*0x0001 Simple dimensionality */ + H5O_SIM_DIM, /*0x0001 Simple dimensionality */ NULL, /*0x0002 Data space (fiber bundle?) */ - NULL, /*0x0003 Simple data type */ + H5O_SIM_DTYPE, /*0x0003 Simple data type */ NULL, /*0x0004 Compound data type */ NULL, /*0x0005 Data storage -- standard object */ NULL, /*0x0006 Data storage -- compact object */ @@ -253,16 +253,25 @@ H5O_load (hdf5_file_t *f, haddr_t addr, const void *_data) HRETURN_ERROR (H5E_OHDR, H5E_CANTINIT, NULL); } - mesgno = oh->nmesgs++; - if (mesgno>=nmesgs) { - HRETURN_ERROR (H5E_OHDR, H5E_CANTLOAD, NULL); + if (H5O_NULL_ID==id && oh->nmesgs>0 && + H5O_NULL_ID==oh->mesg[oh->nmesgs-1].type->id && + oh->mesg[oh->nmesgs-1].chunkno==chunkno) { + /* combine adjacent null messages */ + mesgno = oh->nmesgs - 1; + oh->mesg[mesgno].raw_size += 4 + mesg_size; + } else { + /* new message */ + mesgno = oh->nmesgs++; + if (mesgno>=nmesgs) { + HRETURN_ERROR (H5E_OHDR, H5E_CANTLOAD, NULL); + } + oh->mesg[mesgno].type = message_type_g[id]; + oh->mesg[mesgno].dirty = FALSE; + oh->mesg[mesgno].native = NULL; + oh->mesg[mesgno].raw = p; + oh->mesg[mesgno].raw_size = mesg_size; + oh->mesg[mesgno].chunkno = chunkno; } - oh->mesg[mesgno].type = message_type_g[id]; - oh->mesg[mesgno].dirty = FALSE; - oh->mesg[mesgno].native = NULL; - oh->mesg[mesgno].raw = p; - oh->mesg[mesgno].raw_size = mesg_size; - oh->mesg[mesgno].chunkno = chunkno; } assert (p == oh->chunk[chunkno].image + chunk_size); @@ -403,10 +412,8 @@ H5O_flush (hdf5_file_t *f, hbool_t destroy, haddr_t addr, H5O_t *oh) /* destroy messages */ for (i=0; inmesgs; i++) { - if (oh->mesg[i].native) { - H5O_reset (oh->mesg[i].type, oh->mesg[i].native); - oh->mesg[i].native = H5MM_xfree (oh->mesg[i].native); - } + H5O_reset (oh->mesg[i].type, oh->mesg[i].native); + oh->mesg[i].native = H5MM_xfree (oh->mesg[i].native); } oh->mesg = H5MM_xfree (oh->mesg); @@ -441,14 +448,16 @@ herr_t H5O_reset (const H5O_class_t *type, void *native) { FUNC_ENTER (H5O_reset, NULL, FAIL); - - if (type->reset) { - if ((type->reset)(native)<0) { - /* reset class method failed */ - HRETURN_ERROR (H5E_OHDR, H5E_CANTINIT, FAIL); + + if (native) { + if (type->reset) { + if ((type->reset)(native)<0) { + /* reset class method failed */ + HRETURN_ERROR (H5E_OHDR, H5E_CANTINIT, FAIL); + } + } else { + HDmemset (native, 0, type->native_size); } - } else { - HDmemset (native, 0, type->native_size); } FUNC_LEAVE (SUCCEED); @@ -776,6 +785,15 @@ H5O_modify (hdf5_file_t *f, haddr_t addr, H5G_entry_t *ent, * the sequence numbers to change for subsequent messages of * the same type. * + * If the messaage was cached in the symbol table entry then + * the type field of the symbol table entry is changed to + * H5G_NOTHING_CACHED and the ENT_MODIFIED argument will point + * to non-zero (the ENT_MODIFIED argument is unchanged if + * the ENT type field doesn't change). + * + * No attempt is made to join adjacent free areas of the + * object header into a single larger free area. + * * Return: Success: SUCCEED * * Failure: FAIL @@ -790,11 +808,43 @@ H5O_modify (hdf5_file_t *f, haddr_t addr, H5G_entry_t *ent, */ herr_t H5O_remove (hdf5_file_t *f, haddr_t addr, H5G_entry_t *ent, - const H5O_class_t *type, intn sequence) + hbool_t *ent_modified, const H5O_class_t *type, intn sequence) { + H5O_t *oh = NULL; + intn i, seq; + FUNC_ENTER (H5O_remove, NULL, FAIL); - fprintf (stderr, "H5O_remove: not implemented yet (no-op)!\n"); + /* check args */ + assert (f); + assert (addr>=0); + assert (type); + + /* load the object header */ + if (NULL==(oh=H5AC_find (f, H5AC_OHDR, addr, NULL))) { + HRETURN_ERROR (H5E_OHDR, H5E_CANTLOAD, FAIL); + } + + for (i=seq=0; inmesgs; i++) { + if (type->id != oh->mesg[i].type->id) continue; + if (seq++ == sequence || H5O_ALL==sequence) { + + /* clear symbol table entry cache */ + if (ent && type->cache && H5G_NOTHING_CACHED!=ent->type) { + ent->type = H5G_NOTHING_CACHED; + if (ent_modified) *ent_modified = TRUE; + } + + /* change message type to nil and zero it */ + oh->mesg[i].type = H5O_NULL; + HDmemset (oh->mesg[i].raw, 0, oh->mesg[i].raw_size); + H5O_reset (type, oh->mesg[i].native); + oh->mesg[i].native = H5MM_xfree (oh->mesg[i].native); + + oh->mesg[i].dirty = TRUE; + oh->dirty = TRUE; + } + } FUNC_LEAVE (SUCCEED); } @@ -1113,6 +1163,16 @@ H5O_alloc (hdf5_file_t *f, H5O_t *oh, const H5O_class_t *type, size_t size) oh->mesg[idx].raw_size>=size) break; } +#ifdef LATER + /* + * Perhaps if we join adjacent null messages we could make one + * large enough... we leave this as an exercise for future + * programmers :-) This isn't a high priority because when an + * object header is read from disk the null messages are combined + * anyway. + */ +#endif + /* if we didn't find one, then allocate more header space */ if (idx>=oh->nmesgs) { diff --git a/src/H5Oprivate.h b/src/H5Oprivate.h index f097195..0f774d3 100644 --- a/src/H5Oprivate.h +++ b/src/H5Oprivate.h @@ -25,7 +25,7 @@ #include #include -#define H5O_MIN_SIZE 16 /*min obj header data size */ +#define H5O_MIN_SIZE 32 /*min obj header data size */ #define H5O_NMESGS 32 /*initial number of messages */ #define H5O_NCHUNKS 8 /*initial number of chunks */ #define H5O_NEW_MESG (-1) /*new message */ @@ -175,7 +175,8 @@ intn H5O_modify (hdf5_file_t *f, haddr_t addr, H5G_entry_t *ent, hbool_t *ent_modified, const H5O_class_t *type, intn overwrite, const void *mesg); herr_t H5O_remove (hdf5_file_t *f, haddr_t addr, H5G_entry_t *ent, - const H5O_class_t *type, intn sequence); + hbool_t *ent_modified, const H5O_class_t *type, + intn sequence); herr_t H5O_reset (const H5O_class_t *type, void *native); herr_t H5O_debug (hdf5_file_t *f, haddr_t addr, FILE *stream, intn indent, intn fwidth); -- cgit v0.12