From abce343da8b74b493a03efba0805071ccd99d7c4 Mon Sep 17 00:00:00 2001 From: Quincey Koziol Date: Sat, 17 Jun 2006 13:05:03 -0500 Subject: [svn-r12414] Purpose: Bug fix Description: Fix bug which could lead to files with incorrect count of messages in the header for an object. The exact sequence of operations is complicated and is described in the release notes. Solution: Mark merged null header messages as dirty. Platforms tested: FreeBSD 4.11 (sleipnir) Linux 2.4 (chicago) Mac OS/X (amazon) --- release_docs/RELEASE.txt | 41 +++++- src/H5Ocache.c | 1 + test/tmisc.c | 320 +++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 359 insertions(+), 3 deletions(-) diff --git a/release_docs/RELEASE.txt b/release_docs/RELEASE.txt index f6b366e..4d914b8 100644 --- a/release_docs/RELEASE.txt +++ b/release_docs/RELEASE.txt @@ -49,9 +49,7 @@ New Features configure option, it was never up to production standards anyway. -QAK 2006/4/20 - Added a --enable-group-revision option to configure, to enable - segregating the ongoing work on changing the file format. DO - NOT ENABLE THIS OPTION! It is strictly for internal library - development! -QAK 2006/4/14 + segregating the ongoing work on changing the file format. .-"""""-. / \ @@ -63,6 +61,8 @@ New Features .-.-'_.-' `-----' '-._'-.-. (,_.'` `'._,) + DO NOT ENABLE THIS OPTION! It is strictly for internal library + development! -QAK 2006/4/14 - Added a macro hdf5_mpi_special_collective_io_works to filter out some mpi-io packages that don't support collective IO for no IO contributions in some processes. -KY 2006/2/16 @@ -468,6 +468,41 @@ Bug Fixes since HDF5-1.6.0 release Library ------- + - Fixed file corruption bug which could write an incorrect number of + messages to an object's header under certain circumstances. + Generally, the sequence of actions to generate this bug looks + like this: + - Create an object + - Close the file + - Re-open the file + - Add 2 (or more) attributes to the object + - Close the file + - Re-open the file + - Delete one of the attributes on the object + - Add a smaller attribute to the object + - Delete the smaller atttribute on the object + - Add a larger attribute on the object + + After this, the number of header messages stored for the object + will be off by one. Other sequences of modifying attributes on an + object could also trigger this bug. If you are opening an + object and the bottom few messages of the HDF5 error stack + resembles this, the object has been affected by this bug: + + #007: ../../hdf5_v1.6/src/H5C.c line 3887 in H5C_load_entry(): unable to load entry + major(08): Meta data cache layer + minor(40): Unable to load metadata into cache + #008: ../../hdf5_v1.6/src/H5Ocache.c line 332 in H5O_load(): corrupt object header - too few messages + major(12): Object header layer + minor(40): Unable to load metadata into cache + + Specifically, "corrupt object header" is the best string to search + for in the HDF5 error stack output. + + If your files have been affected by this bug, or you are concerned + that your files might have been, please contact the HDF Helpdesk + at hdfhelp@ncsa.uiuc.edu for a tool to detect and repair files + affected by this problem. QAK - 2006/6/16 - Fixed various problems with retrieving names of objects, especially with mounted files. QAK - 2005/12/25 - Fixed core dump when closing root groups opened through two different diff --git a/src/H5Ocache.c b/src/H5Ocache.c index 4cd5760..ae98df7 100644 --- a/src/H5Ocache.c +++ b/src/H5Ocache.c @@ -261,6 +261,7 @@ H5O_load(H5F_t *f, hid_t dxpl_id, haddr_t addr, const void UNUSED * _udata1, /* combine adjacent null messages */ mesgno = oh->nmesgs - 1; oh->mesg[mesgno].raw_size += H5O_SIZEOF_MSGHDR(f) + mesg_size; + oh->mesg[mesgno].dirty = TRUE; merged_null_msgs++; } else { /* new message */ diff --git a/test/tmisc.c b/test/tmisc.c index c114048..ca405c7 100644 --- a/test/tmisc.c +++ b/test/tmisc.c @@ -272,6 +272,19 @@ unsigned m13_rdata[MISC13_DIM1][MISC13_DIM2]; /* Data read from dataset #define MISC24_DATATYPE_NAME "datatype" #define MISC24_DATATYPE_LINK "datatype_link" +/* Definitions for misc. test #25 */ +#define MISC25_FILE "foo.h5" +#define MISC25_GROUP0_NAME "grp0" +#define MISC25_GROUP1_NAME "/grp0/grp1" +#define MISC25_GROUP2_NAME "/grp0/grp2" +#define MISC25_GROUP3_NAME "/grp0/grp3" +#define MISC25_ATTR1_NAME "_long attribute_" +#define MISC25_ATTR1_LEN 11 +#define MISC25_ATTR2_NAME "_short attr__" +#define MISC25_ATTR2_LEN 11 +#define MISC25_ATTR3_NAME "_short attr__" +#define MISC25_ATTR3_LEN 1 + /**************************************************************** ** ** test_misc1(): test unlinking a dataset from a group and immediately @@ -4224,6 +4237,311 @@ test_misc24(void) /**************************************************************** ** +** test_misc25(): Exercise null object header message merge bug +** +****************************************************************/ +static void +test_misc25(void) +{ + hid_t fid; /* File ID */ + hid_t gid, gid2, gid3; /* Group IDs */ + hid_t aid; /* Attribute ID */ + hid_t sid; /* Dataspace ID */ + hid_t tid; /* Datatype ID */ + herr_t ret; /* Generic return value */ + + /* Output message about test being performed */ + MESSAGE(5, ("Exercise null object header message bug\n")); + + /* Create file */ + fid = H5Fcreate(MISC25_FILE, H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fcreate"); + + /* Create top group */ + gid = H5Gcreate(fid, MISC25_GROUP0_NAME, (size_t)0); + CHECK(gid, FAIL, "H5Gcreate"); + + /* Close top group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Create first group */ + gid = H5Gcreate(fid, MISC25_GROUP1_NAME, (size_t)0); + CHECK(gid, FAIL, "H5Gcreate"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Create second group */ + gid2 = H5Gcreate(fid, MISC25_GROUP2_NAME, (size_t)0); + CHECK(gid2, FAIL, "H5Gcreate"); + + /* Close second group */ + ret = H5Gclose(gid2); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Create dataspace for attribute */ + sid = H5Screate(H5S_SCALAR); + CHECK(sid, FAIL, "H5Screate"); + + /* Create dataype for attribute */ + tid = H5Tcopy(H5T_C_S1); + CHECK(tid, FAIL, "H5Tcopy"); + ret = H5Tset_size(tid, MISC25_ATTR1_LEN); + CHECK(ret, FAIL, "H5Tset_size"); + + /* Add 1st attribute on first group */ + aid = H5Acreate(gid, MISC25_ATTR1_NAME, tid, sid, H5P_DEFAULT); + CHECK(aid, FAIL, "H5Acreate"); + + /* Close dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); + + /* Close datatype */ + ret = H5Tclose(tid); + CHECK(ret, FAIL, "H5Tclose"); + + /* Close attribute */ + ret = H5Aclose(aid); + CHECK(ret, FAIL, "H5Aclose"); + + /* Create dataspace for 2nd attribute */ + sid = H5Screate(H5S_SCALAR); + CHECK(sid, FAIL, "H5Screate"); + + /* Create dataype for attribute */ + tid = H5Tcopy(H5T_C_S1); + CHECK(tid, FAIL, "H5Tcopy"); + ret = H5Tset_size(tid, MISC25_ATTR2_LEN); + CHECK(ret, FAIL, "H5Tset_size"); + + /* Add 2nd attribute on first group */ + aid = H5Acreate(gid, MISC25_ATTR2_NAME, tid, sid, H5P_DEFAULT); + CHECK(aid, FAIL, "H5Acreate"); + + /* Close dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); + + /* Close datatype */ + ret = H5Tclose(tid); + CHECK(ret, FAIL, "H5Tclose"); + + /* Close 2nd attribute */ + ret = H5Aclose(aid); + CHECK(ret, FAIL, "H5Aclose"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Create third group */ + gid3 = H5Gcreate(fid, MISC25_GROUP3_NAME, (size_t)0); + CHECK(gid3, FAIL, "H5Gcreate"); + + /* Close third group */ + ret = H5Gclose(gid3); + CHECK(ret, FAIL, "H5Gclose"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Delete 2nd attribute */ + ret = H5Adelete(gid, MISC25_ATTR2_NAME); + CHECK(ret, FAIL, "H5Adelete"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Create dataspace for 3rd attribute */ + sid = H5Screate(H5S_SCALAR); + CHECK(sid, FAIL, "H5Screate"); + + /* Create dataype for attribute */ + tid = H5Tcopy(H5T_C_S1); + CHECK(tid, FAIL, "H5Tcopy"); + ret = H5Tset_size(tid, MISC25_ATTR3_LEN); + CHECK(ret, FAIL, "H5Tset_size"); + + /* Add 3rd attribute on first group (smaller than 2nd attribute) */ + aid = H5Acreate(gid, MISC25_ATTR3_NAME, tid, sid, H5P_DEFAULT); + CHECK(aid, FAIL, "H5Acreate"); + + /* Close dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); + + /* Close datatype */ + ret = H5Tclose(tid); + CHECK(ret, FAIL, "H5Tclose"); + + /* Close 3rd attribute */ + ret = H5Aclose(aid); + CHECK(ret, FAIL, "H5Aclose"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Delete 3rd attribute */ + ret = H5Adelete(gid, MISC25_ATTR3_NAME); + CHECK(ret, FAIL, "H5Adelete"); + + /* Create dataspace for 3rd attribute */ + sid = H5Screate(H5S_SCALAR); + CHECK(sid, FAIL, "H5Screate"); + + /* Create dataype for attribute */ + tid = H5Tcopy(H5T_C_S1); + CHECK(tid, FAIL, "H5Tcopy"); + ret = H5Tset_size(tid, MISC25_ATTR2_LEN); + CHECK(ret, FAIL, "H5Tset_size"); + + /* Re-create 2nd attribute on first group */ + aid = H5Acreate(gid, MISC25_ATTR2_NAME, tid, sid, H5P_DEFAULT); + CHECK(aid, FAIL, "H5Acreate"); + + /* Close dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); + + /* Close datatype */ + ret = H5Tclose(tid); + CHECK(ret, FAIL, "H5Tclose"); + + /* Close 2nd attribute */ + ret = H5Aclose(aid); + CHECK(ret, FAIL, "H5Aclose"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Delete 2nd attribute */ + ret = H5Adelete(gid, MISC25_ATTR2_NAME); + CHECK(ret, FAIL, "H5Adelete"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); + + + /* Re-open file */ + fid = H5Fopen(MISC25_FILE, H5F_ACC_RDWR, H5P_DEFAULT); + CHECK(fid, FAIL, "H5Fopen"); + + /* Re-open first group */ + gid = H5Gopen(fid, MISC25_GROUP1_NAME); + CHECK(gid, FAIL, "H5Gopen"); + + /* Create dataspace for 3rd attribute */ + sid = H5Screate(H5S_SCALAR); + CHECK(sid, FAIL, "H5Screate"); + + /* Create dataype for attribute */ + tid = H5Tcopy(H5T_C_S1); + CHECK(tid, FAIL, "H5Tcopy"); + ret = H5Tset_size(tid, MISC25_ATTR2_LEN); + CHECK(ret, FAIL, "H5Tset_size"); + + /* Re-create 2nd attribute on first group */ + aid = H5Acreate(gid, MISC25_ATTR2_NAME, tid, sid, H5P_DEFAULT); + CHECK(aid, FAIL, "H5Acreate"); + + /* Close dataspace */ + ret = H5Sclose(sid); + CHECK(ret, FAIL, "H5Sclose"); + + /* Close datatype */ + ret = H5Tclose(tid); + CHECK(ret, FAIL, "H5Tclose"); + + /* Close 2nd attribute */ + ret = H5Aclose(aid); + CHECK(ret, FAIL, "H5Aclose"); + + /* Close first group */ + ret = H5Gclose(gid); + CHECK(ret, FAIL, "H5Gclose"); + + /* Close file */ + ret = H5Fclose(fid); + CHECK(ret, FAIL, "H5Fclose"); +} /* end test_misc25() */ + +/**************************************************************** +** ** test_misc(): Main misc. test routine. ** ****************************************************************/ @@ -4261,6 +4579,7 @@ test_misc(void) test_misc23(); /* Test intermediate group creation */ #endif /* H5_GROUP_REVISION */ test_misc24(); /* Test inappropriate API opens of objects */ + test_misc25(); /* Exercise null object header message merge bug */ } /* test_misc() */ @@ -4311,5 +4630,6 @@ cleanup_misc(void) #endif /* H5_HAVE_FILTER_SZIP */ HDremove(MISC23_FILE); HDremove(MISC24_FILE); + HDremove(MISC25_FILE); } -- cgit v0.12