summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--release_docs/RELEASE.txt2
-rw-r--r--src/H5FDcore.c125
-rw-r--r--test/links.c633
3 files changed, 413 insertions, 347 deletions
diff --git a/release_docs/RELEASE.txt b/release_docs/RELEASE.txt
index 84c7cf7..a04b15c 100644
--- a/release_docs/RELEASE.txt
+++ b/release_docs/RELEASE.txt
@@ -208,6 +208,8 @@ Bug Fixes since HDF5-1.8.0 release
Library
-------
+ - Files can now be concurrently opened more than once using the core file
+ driver, as long as the backing store is used. (NAF - 2010/03/09)
- Added support for H5O_COPY_EXPAND_EXT_LINK_FLAG to H5Ocopy. External
links will now be expanded if this flag is set.
(NAF - 2010/03/05 - 1733)
diff --git a/src/H5FDcore.c b/src/H5FDcore.c
index 1333995..3a56524 100644
--- a/src/H5FDcore.c
+++ b/src/H5FDcore.c
@@ -52,6 +52,31 @@ typedef struct H5FD_core_t {
size_t increment; /*multiples for mem allocation */
hbool_t backing_store; /*write to file name on flush */
int fd; /*backing store file descriptor */
+ /* Information for determining uniqueness of a file with a backing store */
+#ifndef _WIN32
+ /*
+ * On most systems the combination of device and i-node number uniquely
+ * identify a file.
+ */
+ dev_t device; /*file device number */
+#ifdef H5_VMS
+ ino_t inode[3]; /*file i-node number */
+#else
+ ino_t inode; /*file i-node number */
+#endif /*H5_VMS*/
+#else
+ /*
+ * On _WIN32 the low-order word of a unique identifier associated with the
+ * file and the volume serial number uniquely identify a file. This number
+ * (which, both? -rpm) may change when the system is restarted or when the
+ * file is opened. After a process opens a file, the identifier is
+ * constant until the file is closed. An application can use this
+ * identifier and the volume serial number to determine whether two
+ * handles refer to the same file.
+ */
+ DWORD fileindexlo;
+ DWORD fileindexhi;
+#endif
hbool_t dirty; /*changes not saved? */
} H5FD_core_t;
@@ -391,6 +416,10 @@ H5FD_core_open(const char *name, unsigned flags, hid_t fapl_id,
H5FD_core_t *file=NULL;
H5FD_core_fapl_t *fa=NULL;
H5P_genplist_t *plist; /* Property list pointer */
+#ifdef _WIN32
+ HFILE filehandle;
+ struct _BY_HANDLE_FILE_INFORMATION fileinfo;
+#endif
h5_stat_t sb;
int fd=-1;
H5FD_t *ret_value;
@@ -415,11 +444,14 @@ H5FD_core_open(const char *name, unsigned flags, hid_t fapl_id,
if(H5F_ACC_CREAT & flags) o_flags |= O_CREAT;
if(H5F_ACC_EXCL & flags) o_flags |= O_EXCL;
- /* Open backing store. The only case that backing store is off is when
- * the backing_store flag is off and H5F_ACC_CREAT is on. */
+ /* Open backing store, and get stat() from file. The only case that backing
+ * store is off is when the backing_store flag is off and H5F_ACC_CREAT is
+ * on. */
if(fa->backing_store || !(H5F_ACC_CREAT & flags)) {
if(fa && (fd = HDopen(name, o_flags, 0666)) < 0)
HGOTO_ERROR(H5E_FILE, H5E_CANTOPENFILE, NULL, "unable to open file")
+ if(HDfstat(fd, &sb) < 0)
+ HSYS_GOTO_ERROR(H5E_FILE, H5E_BADFILE, NULL, "unable to fstat file")
} /* end if */
/* Create the new file struct */
@@ -439,13 +471,31 @@ H5FD_core_open(const char *name, unsigned flags, hid_t fapl_id,
/* If save data in backing store. */
file->backing_store = fa->backing_store;
+ if(fd >= 0) {
+ /* Retrieve information for determining uniqueness of file */
+#ifdef _WIN32
+ filehandle = _get_osfhandle(fd);
+ (void)GetFileInformationByHandle((HANDLE)filehandle, &fileinfo);
+ file->fileindexhi = fileinfo.nFileIndexHigh;
+ file->fileindexlo = fileinfo.nFileIndexLow;
+#else /* _WIN32 */
+ file->device = sb.st_dev;
+#ifdef H5_VMS
+ file->inode[0] = sb.st_ino[0];
+ file->inode[1] = sb.st_ino[1];
+ file->inode[2] = sb.st_ino[2];
+#else
+ file->inode = sb.st_ino;
+#endif /* H5_VMS */
+
+#endif /* _WIN32 */
+ } /* end if */
+
/* If an existing file is opened, load the whole file into memory. */
if(!(H5F_ACC_CREAT & flags)) {
size_t size;
- /* stat() file to retrieve its size */
- if(HDfstat(file->fd, &sb) < 0)
- HSYS_GOTO_ERROR(H5E_FILE, H5E_BADFILE, NULL, "unable to fstat file")
+ /* Retrieve file size */
size = (size_t)sb.st_size;
/* Check if we should allocate the memory buffer and read in existing data */
@@ -529,6 +579,11 @@ done:
* Thursday, July 29, 1999
*
* Modifications:
+ * Neil Fortner
+ * Tuesday, March 9, 2010
+ * Modified function to compare low level file information if
+ * a backing store is opened for both files, similar to the
+ * sec2 file driver.
*
*-------------------------------------------------------------------------
*/
@@ -537,28 +592,62 @@ H5FD_core_cmp(const H5FD_t *_f1, const H5FD_t *_f2)
{
const H5FD_core_t *f1 = (const H5FD_core_t*)_f1;
const H5FD_core_t *f2 = (const H5FD_core_t*)_f2;
- int ret_value;
+ int ret_value = 0;
FUNC_ENTER_NOAPI(H5FD_core_cmp, FAIL)
- if (NULL==f1->name && NULL==f2->name) {
- if (f1<f2)
+ if(f1->fd >= 0 && f2->fd >= 0) {
+ /* Compare low level file information for backing store */
+#ifdef _WIN32
+ if (f1->fileindexhi < f2->fileindexhi) HGOTO_DONE(-1)
+ if (f1->fileindexhi > f2->fileindexhi) HGOTO_DONE(1)
+
+ if (f1->fileindexlo < f2->fileindexlo) HGOTO_DONE(-1)
+ if (f1->fileindexlo > f2->fileindexlo) HGOTO_DONE(1)
+
+#else
+#ifdef H5_DEV_T_IS_SCALAR
+ if (f1->device < f2->device) HGOTO_DONE(-1)
+ if (f1->device > f2->device) HGOTO_DONE(1)
+#else /* H5_DEV_T_IS_SCALAR */
+ /* If dev_t isn't a scalar value on this system, just use memcmp to
+ * determine if the values are the same or not. The actual return value
+ * shouldn't really matter...
+ */
+ if(HDmemcmp(&(f1->device),&(f2->device),sizeof(dev_t))<0) HGOTO_DONE(-1)
+ if(HDmemcmp(&(f1->device),&(f2->device),sizeof(dev_t))>0) HGOTO_DONE(1)
+#endif /* H5_DEV_T_IS_SCALAR */
+
+#ifndef H5_VMS
+ if (f1->inode < f2->inode) HGOTO_DONE(-1)
+ if (f1->inode > f2->inode) HGOTO_DONE(1)
+#else
+ if(HDmemcmp(&(f1->inode),&(f2->inode),3*sizeof(ino_t))<0) HGOTO_DONE(-1)
+ if(HDmemcmp(&(f1->inode),&(f2->inode),3*sizeof(ino_t))>0) HGOTO_DONE(1)
+#endif /* H5_VMS */
+
+#endif /*_WIN32*/
+ } /* end if */
+ else {
+ if (NULL==f1->name && NULL==f2->name) {
+ if (f1<f2)
+ HGOTO_DONE(-1)
+ if (f1>f2)
+ HGOTO_DONE(1)
+ HGOTO_DONE(0)
+ } /* end if */
+
+ if (NULL==f1->name)
HGOTO_DONE(-1)
- if (f1>f2)
+ if (NULL==f2->name)
HGOTO_DONE(1)
- HGOTO_DONE(0)
- }
- if (NULL==f1->name)
- HGOTO_DONE(-1)
- if (NULL==f2->name)
- HGOTO_DONE(1)
-
- ret_value = HDstrcmp(f1->name, f2->name);
+ ret_value = HDstrcmp(f1->name, f2->name);
+ } /* end else */
done:
FUNC_LEAVE_NOAPI(ret_value)
-}
+} /* end H5FD_core_cmp() */
/*-------------------------------------------------------------------------
diff --git a/test/links.c b/test/links.c
index 9146a3e..f636413 100644
--- a/test/links.c
+++ b/test/links.c
@@ -2190,7 +2190,7 @@ external_link_mult(hid_t fapl, hbool_t new_format)
*-------------------------------------------------------------------------
*/
static int
-external_link_self(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
+external_link_self(hid_t fapl, hbool_t new_format)
{
hid_t fid = (-1); /* File ID */
hid_t gid = (-1), gid2 = (-1); /* Group IDs */
@@ -2205,118 +2205,109 @@ external_link_self(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
else
TESTING("external link to self")
- /* Skip test when using core VFD, since it doesn't re-open file when linking
- * to same file.
- */
- if(HDstrcmp(env_h5_drvr, "core")) {
- /* Set up filename */
- h5_fixname(FILENAME[1], fapl, filename1, sizeof filename1);
- h5_fixname(FILENAME[2], fapl, filename2, sizeof filename1);
- h5_fixname(FILENAME[3], fapl, filename3, sizeof filename1);
+ /* Set up filename */
+ h5_fixname(FILENAME[1], fapl, filename1, sizeof filename1);
+ h5_fixname(FILENAME[2], fapl, filename2, sizeof filename1);
+ h5_fixname(FILENAME[3], fapl, filename3, sizeof filename1);
- /* Create file */
- if((fid = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ /* Create file */
+ if((fid = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- /* Create an lcpl with intermediate group creation set */
- if((lcpl_id = H5Pcreate(H5P_LINK_CREATE)) < 0) TEST_ERROR
- if(H5Pset_create_intermediate_group(lcpl_id, TRUE) < 0) TEST_ERROR
+ /* Create an lcpl with intermediate group creation set */
+ if((lcpl_id = H5Pcreate(H5P_LINK_CREATE)) < 0) TEST_ERROR
+ if(H5Pset_create_intermediate_group(lcpl_id, TRUE) < 0) TEST_ERROR
- /* Create a series of groups within the file: /A/B and /X/Y/Z */
- if((gid = H5Gcreate2(fid, "A/B", lcpl_id, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if((gid = H5Gcreate2(fid, "X/Y", lcpl_id, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Create a series of groups within the file: /A/B and /X/Y/Z */
+ if((gid = H5Gcreate2(fid, "A/B", lcpl_id, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if((gid = H5Gcreate2(fid, "X/Y", lcpl_id, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Pclose (lcpl_id) < 0) TEST_ERROR
+ if(H5Pclose (lcpl_id) < 0) TEST_ERROR
- /* Create external link to own root group*/
- if(H5Lcreate_external(filename1, "/X", fid, "A/B/C", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ /* Create external link to own root group*/
+ if(H5Lcreate_external(filename1, "/X", fid, "A/B/C", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- /* Open object through external link */
- if((gid = H5Gopen2(fid, "A/B/C/", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Open object through external link */
+ if((gid = H5Gopen2(fid, "A/B/C/", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Check name */
- if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
- if(HDstrcmp(objname, "/X")) TEST_ERROR
+ /* Check name */
+ if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
+ if(HDstrcmp(objname, "/X")) TEST_ERROR
- /* Create object through external link */
- if((gid2 = H5Gcreate2(gid, "new_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ /* Create object through external link */
+ if((gid2 = H5Gcreate2(gid, "new_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- /* Close created group */
- if(H5Gclose(gid2) < 0) TEST_ERROR
+ /* Close created group */
+ if(H5Gclose(gid2) < 0) TEST_ERROR
- /* Close object opened through external link */
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Close object opened through external link */
+ if(H5Gclose(gid) < 0) TEST_ERROR
- /* Check on object created */
- if((gid = H5Gopen2(fid, "X/new_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Check on object created */
+ if((gid = H5Gopen2(fid, "X/new_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Check name */
- if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
- if(HDstrcmp(objname, "/X/new_group")) TEST_ERROR
+ /* Check name */
+ if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
+ if(HDstrcmp(objname, "/X/new_group")) TEST_ERROR
- /* Close opened object */
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Close opened object */
+ if(H5Gclose(gid) < 0) TEST_ERROR
- /* Close first file */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close first file */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Complicate things. Use this file as an intermediate file in a chain
- * of external links that will go: file2 -> file1 -> file1 -> file3
- */
+ /* Complicate things. Use this file as an intermediate file in a chain
+ * of external links that will go: file2 -> file1 -> file1 -> file3
+ */
- /* Create file2 with an external link to file1 */
- if((fid=H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ /* Create file2 with an external link to file1 */
+ if((fid=H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if(H5Lcreate_external(filename1, "/A", fid, "ext_link", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename1, "/A", fid, "ext_link", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- /* Close file2 */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close file2 */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Create file3 as a target */
- if((fid=H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((gid = H5Gcreate2(fid, "end", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Create file3 as a target */
+ if((fid=H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((gid = H5Gcreate2(fid, "end", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Open file1 and create an extlink pointing to file3 */
- if((fid=H5Fopen(filename1, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
+ /* Open file1 and create an extlink pointing to file3 */
+ if((fid=H5Fopen(filename1, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
- if(H5Lcreate_external(filename3, "/", fid, "/X/Y/Z", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename3, "/", fid, "/X/Y/Z", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- /* Close file1 */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close file1 */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Re-open file2 and traverse through file1 (with its recursive extlink) to file3 */
- if((fid=H5Fopen(filename2, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
+ /* Re-open file2 and traverse through file1 (with its recursive extlink) to file3 */
+ if((fid=H5Fopen(filename2, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
- if((gid = H5Gopen2(fid, "ext_link/B/C/Y/Z/end", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((gid = H5Gopen2(fid, "ext_link/B/C/Y/Z/end", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Create object through external link */
- if((gid2 = H5Gcreate2(gid, "newer_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ /* Create object through external link */
+ if((gid2 = H5Gcreate2(gid, "newer_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- /* Cleanup */
- if(H5Gclose(gid2) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Cleanup */
+ if(H5Gclose(gid2) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Open up file3 and make sure the object was created successfully */
- if((fid = H5Fopen(filename3, H5F_ACC_RDWR, fapl)) < 0) FAIL_STACK_ERROR
+ /* Open up file3 and make sure the object was created successfully */
+ if((fid = H5Fopen(filename3, H5F_ACC_RDWR, fapl)) < 0) FAIL_STACK_ERROR
- if((gid = H5Gopen2(fid, "end/newer_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((gid = H5Gopen2(fid, "end/newer_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Cleanup */
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Cleanup */
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Fclose(fid) < 0) TEST_ERROR
- PASSED();
- } /* end if */
- else {
- SKIPPED();
- puts(" Current VFD can't reopen same file through external link");
- } /* end else */
+ PASSED();
return 0;
@@ -2356,7 +2347,7 @@ external_link_self(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
*-------------------------------------------------------------------------
*/
static int
-external_link_pingpong(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
+external_link_pingpong(hid_t fapl, hbool_t new_format)
{
hid_t fid = (-1); /* File ID */
hid_t gid = (-1), gid2 = (-1); /* Group IDs */
@@ -2369,86 +2360,77 @@ external_link_pingpong(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
else
TESTING("external links back and forth")
- /* Skip test when using core VFD, since it doesn't re-open file when linking
- * to same file.
- */
- if(HDstrcmp(env_h5_drvr, "core")) {
- /* Set up filenames */
- h5_fixname(FILENAME[3], fapl, filename1, sizeof filename1);
- h5_fixname(FILENAME[4], fapl, filename2, sizeof filename2);
+ /* Set up filenames */
+ h5_fixname(FILENAME[3], fapl, filename1, sizeof filename1);
+ h5_fixname(FILENAME[4], fapl, filename2, sizeof filename2);
- /* Create first file */
- if((fid=H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ /* Create first file */
+ if((fid=H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- /* Create external links for chain */
- if(H5Lcreate_external(filename2, "/link2", fid, "link1", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename2, "/link4", fid, "link3", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename2, "/link6", fid, "link5", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ /* Create external links for chain */
+ if(H5Lcreate_external(filename2, "/link2", fid, "link1", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename2, "/link4", fid, "link3", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename2, "/link6", fid, "link5", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- /* Create final object */
- if((gid = H5Gcreate2(fid, "final", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Create final object */
+ if((gid = H5Gcreate2(fid, "final", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
- /* Close file */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close file */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Create second file */
- if((fid=H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ /* Create second file */
+ if((fid=H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- /* Create external links for chain */
- if(H5Lcreate_external(filename1, "/link3", fid, "link2", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename1, "/link5", fid, "link4", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename1, "/final", fid, "link6", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ /* Create external links for chain */
+ if(H5Lcreate_external(filename1, "/link3", fid, "link2", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename1, "/link5", fid, "link4", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename1, "/final", fid, "link6", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- /* Close file */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close file */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Open first file */
- if((fid=H5Fopen(filename1, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
+ /* Open first file */
+ if((fid=H5Fopen(filename1, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
- /* Open object through external link */
- if((gid = H5Gopen2(fid, "link1", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Open object through external link */
+ if((gid = H5Gopen2(fid, "link1", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Check name */
- if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
- if(HDstrcmp(objname, "/final")) TEST_ERROR
+ /* Check name */
+ if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
+ if(HDstrcmp(objname, "/final")) TEST_ERROR
- /* Create object in external file */
- if((gid2 = H5Gcreate2(gid, "new_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ /* Create object in external file */
+ if((gid2 = H5Gcreate2(gid, "new_group", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- /* Close group in external file */
- if(H5Gclose(gid2) < 0) TEST_ERROR
+ /* Close group in external file */
+ if(H5Gclose(gid2) < 0) TEST_ERROR
- /* Close external object (lets first file close) */
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Close external object (lets first file close) */
+ if(H5Gclose(gid) < 0) TEST_ERROR
- /* Close first file */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close first file */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- /* Open first file again and check on object created */
- if((fid = H5Fopen(filename1, H5F_ACC_RDONLY, fapl)) < 0) TEST_ERROR
+ /* Open first file again and check on object created */
+ if((fid = H5Fopen(filename1, H5F_ACC_RDONLY, fapl)) < 0) TEST_ERROR
- /* Open object created through external link */
- if((gid = H5Gopen2(fid, "/final/new_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Open object created through external link */
+ if((gid = H5Gopen2(fid, "/final/new_group", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Check name */
- if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
- if(HDstrcmp(objname, "/final/new_group")) TEST_ERROR
+ /* Check name */
+ if(H5Iget_name(gid, objname, (size_t)NAME_BUF_SIZE) < 0) TEST_ERROR
+ if(HDstrcmp(objname, "/final/new_group")) TEST_ERROR
- /* Close opened object */
- if(H5Gclose(gid) < 0) TEST_ERROR
+ /* Close opened object */
+ if(H5Gclose(gid) < 0) TEST_ERROR
- /* Close first file */
- if(H5Fclose(fid) < 0) TEST_ERROR
+ /* Close first file */
+ if(H5Fclose(fid) < 0) TEST_ERROR
- PASSED();
- } /* end if */
- else {
- SKIPPED();
- puts(" Current VFD can't reopen same file through external link");
- } /* end else */
+ PASSED();
return 0;
@@ -5993,7 +5975,7 @@ error:
*-------------------------------------------------------------------------
*/
static int
-external_link_closing(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
+external_link_closing(hid_t fapl, hbool_t new_format)
{
hid_t fid1 = (-1), fid2 = (-1), fid3 = (-1), fid4=(-1);
hid_t gid=(-1), tid=(-1), tid2=(-1), sid=(-1), did=(-1);
@@ -6013,194 +5995,185 @@ external_link_closing(const char *env_h5_drvr, hid_t fapl, hbool_t new_format)
else
TESTING("that external files are closed during traversal")
- /* Skip test when using core VFD, since it doesn't re-open file when linking
- * to same file.
+ /* In this test, external links will go from file1 to file2 and from
+ * file2 to file3.
+ * Test that all functions that can traverse external files close
+ * the files they open.
+ * Test that providing unusual paths containing external links can't
+ * make HDF5 forget to close a file it opened.
*/
- if(HDstrcmp(env_h5_drvr, "core")) {
- /* In this test, external links will go from file1 to file2 and from
- * file2 to file3.
- * Test that all functions that can traverse external files close
- * the files they open.
- * Test that providing unusual paths containing external links can't
- * make HDF5 forget to close a file it opened.
- */
- /* Set up filenames */
- h5_fixname(FILENAME[3], fapl, filename1, sizeof filename1);
- h5_fixname(FILENAME[4], fapl, filename2, sizeof filename2);
- h5_fixname(FILENAME[5], fapl, filename3, sizeof filename3);
- h5_fixname(FILENAME[6], fapl, filename4, sizeof filename4);
-
- /* Create four files */
- if((fid1 = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid2 = H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid3 = H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid4 = H5Fcreate(filename4, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
-
- /* Create a dataspace and a datatype so we can create/commit a dataset/datatype in the files */
- dims[0] = 2;
- dims[1] = 2;
- if((sid = H5Screate_simple(2, dims, NULL)) < 0) TEST_ERROR
- if((tid = H5Tcopy(H5T_NATIVE_INT)) < 0) TEST_ERROR
- if((tid2 = H5Tcopy(H5T_NATIVE_INT)) < 0) TEST_ERROR
-
- /* Create external links from each file to the next */
- if(H5Lcreate_external(filename2, "/", fid1, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename3, "/", fid2, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lcreate_external(filename4, "/", fid3, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Close all files but the first */
- if(H5Fclose(fid4) < 0) TEST_ERROR
- if(H5Fclose(fid3) < 0) TEST_ERROR
- if(H5Fclose(fid2) < 0) TEST_ERROR
-
- /* Test creating each kind of object */
- if((gid = H5Gcreate2(fid1, "elink/elink/elink/group1", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Tcommit2(fid1, "elink/elink/elink/type1", tid, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if((did = H5Dcreate2(fid1, "elink/elink/elink/dataset1", tid2, sid, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
-
- /* Close objects */
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Tclose(tid) < 0) TEST_ERROR
- if(H5Dclose(did) < 0) TEST_ERROR
-
- /* Test that getting info works */
- if(H5Lget_info(fid1, "elink/elink/elink/type1", &li, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lget_info(fid1, "elink/elink/elink", &li, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Oget_info_by_name(fid1, "elink/elink/elink/type1", &oi, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Oget_info_by_name(fid1, "elink/elink/elink", &oi, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Test move */
- if(H5Lmove(fid1, "elink/elink/elink/group1", fid1,
- "elink/elink/elink/group1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Open file 4 so we can do some fancy things */
- if((fid4 = H5Fopen(filename4, H5F_ACC_RDWR, fapl)) < 0) FAIL_STACK_ERROR
- if(H5Lmove(fid1, "elink/elink/elink/type1", fid4,
- "type1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
- if(H5Lmove(fid4, "dataset1", fid1,
- "elink/elink/elink/dataset1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
-
- /* Close file 4 again */
- if(H5Fclose(fid4) < 0) FAIL_STACK_ERROR
-
- /* Test copy (as of this test, it uses the same code as move) */
- if(H5Lcopy(fid1, "elink/elink/elink", fid1,
- "elink/elink/elink_copied", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
- if(H5Lcopy(fid1, "elink/elink/elink", fid1,
- "elink/elink/elink/elink_copied2", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
-
- /* Test H5Gset and get comment */
- if(H5Oset_comment_by_name(fid1, "elink/elink/elink/group1_moved", "comment", H5P_DEFAULT) < 0) FAIL_STACK_ERROR
- if(H5Oget_comment_by_name(fid1, "elink/elink/elink/group1_moved", buf, sizeof(buf), H5P_DEFAULT) < 0) FAIL_STACK_ERROR
- if(HDstrcmp(buf, "comment")) TEST_ERROR
-
- /* Test H5*open */
- if((gid = H5Gopen2(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- if((tid = H5Topen2(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- if((did = H5Dopen2(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Close objects */
- if(H5Gclose(gid) < 0) FAIL_STACK_ERROR
- if(H5Tclose(tid) < 0) FAIL_STACK_ERROR
- if(H5Dclose(did) < 0) FAIL_STACK_ERROR
-
- /* Test H5*open2 */
- if((gid = H5Gopen2(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- if((tid = H5Topen2(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- if((did = H5Dopen2(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
- /* Close objects */
- if(H5Gclose(gid) < 0) FAIL_STACK_ERROR
- if(H5Tclose(tid) < 0) FAIL_STACK_ERROR
- if(H5Dclose(did) < 0) FAIL_STACK_ERROR
-
- /* Test H5Oopen */
- if((did = H5Oopen(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Dclose(did) < 0) TEST_ERROR
-
- /* Test H5Fmount */
- if((gid = H5Gcreate2(fid1, "elink/elink/elink/mnt", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- H5E_BEGIN_TRY {
- if(H5Fmount(fid1, "elink/elink/elink/mnt", fid1, H5P_DEFAULT) >= 0) TEST_ERROR
- if(H5Funmount(fid1, "elink/elink/elink/mnt") >= 0) TEST_ERROR
- } H5E_END_TRY
-
- /* Test H5Rcreate */
- if(H5Rcreate(&obj_ref, fid1, "elink/elink/elink/type1_moved", H5R_OBJECT, (-1)) < 0) TEST_ERROR
-
- /* Test unlink */
- if(H5Ldelete(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Ldelete(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Ldelete(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Ldelete(fid1, "elink/elink/elink_copied", H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Ldelete(fid1, "elink/elink/elink/elink_copied2", H5P_DEFAULT) < 0) TEST_ERROR
-
- /* We've tested that the various functions above don't leave files open.
- * Now test that we can't confuse HDF5 by giving unusual paths with external links
- */
- /* Create an external link that points to another external link */
- if((fid2 = H5Fopen(filename2, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
- if(H5Lcreate_external(filename3, "/elink", fid2, "elink2",
- H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Fclose(fid2) < 0) TEST_ERROR
-
- /* Do an external link traversal that recursively calls another external link. */
- if((gid = H5Gcreate2(fid1, "elink/elink2/group2", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
-
- /* Create two more groups so that the last three elements in the path are
- * all within the same external file
- */
- if((gid = H5Gcreate2(fid1, "elink/elink2/group2/group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if((gid = H5Gcreate2(fid1, "elink/elink2/group2/group3/group4", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Oget_info_by_name(fid1, "elink/elink2/group2/group3/group4", &oi, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Add a few regular groups and a soft link in file2 using intermediate group creation */
- if((lcpl_id = H5Pcreate(H5P_LINK_CREATE)) < 0) TEST_ERROR
- if(H5Pset_create_intermediate_group(lcpl_id, TRUE) < 0) TEST_ERROR
- if(H5Lcreate_soft("/elink2", fid1, "elink/file2group1/file2group2/slink",
- lcpl_id, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Try to traverse this path. There are three soft traversals in a row;
- * slink points to (file2)/elink2, which points to (file3)/elink, which
- * points to file 4.
- */
- if((gid = H5Gcreate2(fid1, "elink/file2group1/file2group2/slink/group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Lget_info(fid1, "elink/file2group1/file2group2/slink/group3", &li, H5P_DEFAULT) < 0) TEST_ERROR
-
- /* Some simpler tests */
- if((gid = H5Gcreate2(fid1, "elink/file2group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
- if(H5Gclose(gid) < 0) TEST_ERROR
- if(H5Lget_info(fid1, "elink/file2group3", &li, H5P_DEFAULT) < 0) TEST_ERROR
- if(H5Lget_info(fid1, "elink/elink", &li, H5P_DEFAULT) < 0) TEST_ERROR
-
-
- /* Close file1, the only file that should still be open */
- if(H5Fclose(fid1) < 0) TEST_ERROR
-
- /* Re-create each file. If they are hanging open, these creates will fail */
- if((fid1 = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid2 = H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid3 = H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
- if((fid4 = H5Fcreate(filename4, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
-
- /* Cleanup */
- if(H5Sclose(sid) < 0) TEST_ERROR
- if(H5Tclose(tid2) < 0) TEST_ERROR
- if(H5Fclose(fid4) < 0) TEST_ERROR
- if(H5Fclose(fid3) < 0) TEST_ERROR
- if(H5Fclose(fid2) < 0) TEST_ERROR
- if(H5Fclose(fid1) < 0) TEST_ERROR
+ /* Set up filenames */
+ h5_fixname(FILENAME[3], fapl, filename1, sizeof filename1);
+ h5_fixname(FILENAME[4], fapl, filename2, sizeof filename2);
+ h5_fixname(FILENAME[5], fapl, filename3, sizeof filename3);
+ h5_fixname(FILENAME[6], fapl, filename4, sizeof filename4);
- PASSED();
- } /* end if */
- else {
- SKIPPED();
- puts(" Current VFD can't reopen same file through external link");
- } /* end else */
+ /* Create four files */
+ if((fid1 = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid2 = H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid3 = H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid4 = H5Fcreate(filename4, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+
+ /* Create a dataspace and a datatype so we can create/commit a dataset/datatype in the files */
+ dims[0] = 2;
+ dims[1] = 2;
+ if((sid = H5Screate_simple(2, dims, NULL)) < 0) TEST_ERROR
+ if((tid = H5Tcopy(H5T_NATIVE_INT)) < 0) TEST_ERROR
+ if((tid2 = H5Tcopy(H5T_NATIVE_INT)) < 0) TEST_ERROR
+
+ /* Create external links from each file to the next */
+ if(H5Lcreate_external(filename2, "/", fid1, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename3, "/", fid2, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename4, "/", fid3, "elink", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Close all files but the first */
+ if(H5Fclose(fid4) < 0) TEST_ERROR
+ if(H5Fclose(fid3) < 0) TEST_ERROR
+ if(H5Fclose(fid2) < 0) TEST_ERROR
+
+ /* Test creating each kind of object */
+ if((gid = H5Gcreate2(fid1, "elink/elink/elink/group1", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Tcommit2(fid1, "elink/elink/elink/type1", tid, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if((did = H5Dcreate2(fid1, "elink/elink/elink/dataset1", tid2, sid, H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+
+ /* Close objects */
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Tclose(tid) < 0) TEST_ERROR
+ if(H5Dclose(did) < 0) TEST_ERROR
+
+ /* Test that getting info works */
+ if(H5Lget_info(fid1, "elink/elink/elink/type1", &li, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lget_info(fid1, "elink/elink/elink", &li, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Oget_info_by_name(fid1, "elink/elink/elink/type1", &oi, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Oget_info_by_name(fid1, "elink/elink/elink", &oi, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Test move */
+ if(H5Lmove(fid1, "elink/elink/elink/group1", fid1,
+ "elink/elink/elink/group1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Open file 4 so we can do some fancy things */
+ if((fid4 = H5Fopen(filename4, H5F_ACC_RDWR, fapl)) < 0) FAIL_STACK_ERROR
+ if(H5Lmove(fid1, "elink/elink/elink/type1", fid4,
+ "type1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+ if(H5Lmove(fid4, "dataset1", fid1,
+ "elink/elink/elink/dataset1_moved", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+
+ /* Close file 4 again */
+ if(H5Fclose(fid4) < 0) FAIL_STACK_ERROR
+
+ /* Test copy (as of this test, it uses the same code as move) */
+ if(H5Lcopy(fid1, "elink/elink/elink", fid1,
+ "elink/elink/elink_copied", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+ if(H5Lcopy(fid1, "elink/elink/elink", fid1,
+ "elink/elink/elink/elink_copied2", H5P_DEFAULT, H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+
+ /* Test H5Gset and get comment */
+ if(H5Oset_comment_by_name(fid1, "elink/elink/elink/group1_moved", "comment", H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+ if(H5Oget_comment_by_name(fid1, "elink/elink/elink/group1_moved", buf, sizeof(buf), H5P_DEFAULT) < 0) FAIL_STACK_ERROR
+ if(HDstrcmp(buf, "comment")) TEST_ERROR
+
+ /* Test H5*open */
+ if((gid = H5Gopen2(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((tid = H5Topen2(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((did = H5Dopen2(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Close objects */
+ if(H5Gclose(gid) < 0) FAIL_STACK_ERROR
+ if(H5Tclose(tid) < 0) FAIL_STACK_ERROR
+ if(H5Dclose(did) < 0) FAIL_STACK_ERROR
+
+ /* Test H5*open2 */
+ if((gid = H5Gopen2(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((tid = H5Topen2(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ if((did = H5Dopen2(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) FAIL_STACK_ERROR
+ /* Close objects */
+ if(H5Gclose(gid) < 0) FAIL_STACK_ERROR
+ if(H5Tclose(tid) < 0) FAIL_STACK_ERROR
+ if(H5Dclose(did) < 0) FAIL_STACK_ERROR
+
+ /* Test H5Oopen */
+ if((did = H5Oopen(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Dclose(did) < 0) TEST_ERROR
+
+ /* Test H5Fmount */
+ if((gid = H5Gcreate2(fid1, "elink/elink/elink/mnt", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ H5E_BEGIN_TRY {
+ if(H5Fmount(fid1, "elink/elink/elink/mnt", fid1, H5P_DEFAULT) >= 0) TEST_ERROR
+ if(H5Funmount(fid1, "elink/elink/elink/mnt") >= 0) TEST_ERROR
+ } H5E_END_TRY
+
+ /* Test H5Rcreate */
+ if(H5Rcreate(&obj_ref, fid1, "elink/elink/elink/type1_moved", H5R_OBJECT, (-1)) < 0) TEST_ERROR
+
+ /* Test unlink */
+ if(H5Ldelete(fid1, "elink/elink/elink/group1_moved", H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Ldelete(fid1, "elink/elink/elink/type1_moved", H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Ldelete(fid1, "elink/elink/elink/dataset1_moved", H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Ldelete(fid1, "elink/elink/elink_copied", H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Ldelete(fid1, "elink/elink/elink/elink_copied2", H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* We've tested that the various functions above don't leave files open.
+ * Now test that we can't confuse HDF5 by giving unusual paths with external links
+ */
+ /* Create an external link that points to another external link */
+ if((fid2 = H5Fopen(filename2, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
+ if(H5Lcreate_external(filename3, "/elink", fid2, "elink2",
+ H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Fclose(fid2) < 0) TEST_ERROR
+
+ /* Do an external link traversal that recursively calls another external link. */
+ if((gid = H5Gcreate2(fid1, "elink/elink2/group2", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+
+ /* Create two more groups so that the last three elements in the path are
+ * all within the same external file
+ */
+ if((gid = H5Gcreate2(fid1, "elink/elink2/group2/group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if((gid = H5Gcreate2(fid1, "elink/elink2/group2/group3/group4", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Oget_info_by_name(fid1, "elink/elink2/group2/group3/group4", &oi, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Add a few regular groups and a soft link in file2 using intermediate group creation */
+ if((lcpl_id = H5Pcreate(H5P_LINK_CREATE)) < 0) TEST_ERROR
+ if(H5Pset_create_intermediate_group(lcpl_id, TRUE) < 0) TEST_ERROR
+ if(H5Lcreate_soft("/elink2", fid1, "elink/file2group1/file2group2/slink",
+ lcpl_id, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Try to traverse this path. There are three soft traversals in a row;
+ * slink points to (file2)/elink2, which points to (file3)/elink, which
+ * points to file 4.
+ */
+ if((gid = H5Gcreate2(fid1, "elink/file2group1/file2group2/slink/group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Lget_info(fid1, "elink/file2group1/file2group2/slink/group3", &li, H5P_DEFAULT) < 0) TEST_ERROR
+
+ /* Some simpler tests */
+ if((gid = H5Gcreate2(fid1, "elink/file2group3", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
+ if(H5Gclose(gid) < 0) TEST_ERROR
+ if(H5Lget_info(fid1, "elink/file2group3", &li, H5P_DEFAULT) < 0) TEST_ERROR
+ if(H5Lget_info(fid1, "elink/elink", &li, H5P_DEFAULT) < 0) TEST_ERROR
+
+
+ /* Close file1, the only file that should still be open */
+ if(H5Fclose(fid1) < 0) TEST_ERROR
+
+ /* Re-create each file. If they are hanging open, these creates will fail */
+ if((fid1 = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid2 = H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid3 = H5Fcreate(filename3, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+ if((fid4 = H5Fcreate(filename4, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
+
+ /* Cleanup */
+ if(H5Sclose(sid) < 0) TEST_ERROR
+ if(H5Tclose(tid2) < 0) TEST_ERROR
+ if(H5Fclose(fid4) < 0) TEST_ERROR
+ if(H5Fclose(fid3) < 0) TEST_ERROR
+ if(H5Fclose(fid2) < 0) TEST_ERROR
+ if(H5Fclose(fid1) < 0) TEST_ERROR
+
+ PASSED();
return 0;
@@ -13982,8 +13955,8 @@ main(void)
nerrors += external_link_path(my_fapl, new_format) < 0 ? 1 : 0;
nerrors += external_link_mult(my_fapl, new_format) < 0 ? 1 : 0;
#ifndef H5_CANNOT_OPEN_TWICE
- nerrors += external_link_self(env_h5_drvr, my_fapl, new_format) < 0 ? 1 : 0;
- nerrors += external_link_pingpong(env_h5_drvr, my_fapl, new_format) < 0 ? 1 : 0;
+ nerrors += external_link_self(my_fapl, new_format) < 0 ? 1 : 0;
+ nerrors += external_link_pingpong(my_fapl, new_format) < 0 ? 1 : 0;
nerrors += external_link_toomany(my_fapl, new_format) < 0 ? 1 : 0;
#endif /* H5_CANNOT_OPEN_TWICE */
nerrors += external_link_dangling(my_fapl, new_format) < 0 ? 1 : 0;
@@ -13994,7 +13967,7 @@ main(void)
nerrors += external_link_move(my_fapl, new_format) < 0 ? 1 : 0;
nerrors += external_link_ride(my_fapl, new_format) < 0 ? 1 : 0;
#ifndef H5_CANNOT_OPEN_TWICE
- nerrors += external_link_closing(env_h5_drvr, my_fapl, new_format) < 0 ? 1 : 0;
+ nerrors += external_link_closing(my_fapl, new_format) < 0 ? 1 : 0;
#endif /* H5_CANNOT_OPEN_TWICE */
nerrors += external_link_endian(new_format) < 0 ? 1 : 0;
nerrors += external_link_strong(my_fapl, new_format) < 0 ? 1 : 0;
@@ -14050,7 +14023,9 @@ main(void)
nerrors += obj_visit_by_name(my_fapl, new_format) < 0 ? 1 : 0;
nerrors += obj_visit_stop(my_fapl, new_format) < 0 ? 1 : 0;
nerrors += link_filters(my_fapl, new_format) < 0 ? 1 : 0;
+#ifndef H5_CANNOT_OPEN_TWICE
nerrors += obj_exists(my_fapl, new_format) < 0 ? 1 : 0;
+#endif /* H5_CANNOT_OPEN_TWICE */
/* Keep this test last, it's testing files that are used above */
/* do not do this for files used by external link tests */