mirror of
https://github.com/HDFGroup/hdf5.git
synced 2025-04-18 17:40:55 +08:00
[svn-r17860] Description:
"Normalize" object names for external links, making them into the same form as used for soft links. Begin the process of adding more printf-like information to library error reporting. HGOTO_ERROR() and HDONE_ERROR() macros can now use the last parameter (a string) like a printf() formatting string and pass extra parameters with additional information. (For example, see the HGOTO_ERROR macros in H5FD_sec2_read() in src/H5FDsec2.c) Tested on: FreeBSD/32 6.3 (duty) in debug mode FreeBSD/64 6.3 (liberty) w/C++ & FORTRAN, in debug mode Linux/32 2.6 (jam) w/PGI compilers, w/default API=1.8.x, w/C++ & FORTRAN, w/threadsafe, in debug mode Linux/64-amd64 2.6 (smirom) w/Intel compilers, w/default API=1.6.x, w/C++ & FORTRAN, in production mode Solaris/32 2.10 (linew) w/deprecated symbols disabled, w/C++ & FORTRAN, w/szip filter, in production mode Linux/64-ia64 2.6 (cobalt) w/Intel compilers, w/C++ & FORTRAN, in production mode Linux/64-ia64 2.4 (tg-login3) w/parallel, w/FORTRAN, in debug mode Linux/64-amd64 2.6 (abe) w/parallel, w/FORTRAN, in production mode Mac OS X/32 10.6.2 (amazon) in debug mode Mac OS X/32 10.6.2 (amazon) w/C++ & FORTRAN, w/threadsafe, in production mode
This commit is contained in:
parent
e8f31a2479
commit
a83a4ece41
@ -32,14 +32,14 @@ typedef struct H5E_t H5E_t;
|
||||
* and a FUNC_LEAVE() within a function body. The arguments are the major
|
||||
* error number, the minor error number, and a description of the error.
|
||||
*/
|
||||
#define HERROR(maj_id, min_id, str) H5E_push_stack(NULL, __FILE__, FUNC, __LINE__, H5E_ERR_CLS_g, maj_id, min_id, str)
|
||||
#define HERROR(maj_id, min_id, ...) H5E_printf_stack(NULL, __FILE__, FUNC, __LINE__, H5E_ERR_CLS_g, maj_id, min_id, __VA_ARGS__)
|
||||
|
||||
/*
|
||||
* HCOMMON_ERROR macro, used by HDONE_ERROR and HGOTO_ERROR
|
||||
* (Shouldn't need to be used outside this header file)
|
||||
*/
|
||||
#define HCOMMON_ERROR(maj, min, str) \
|
||||
HERROR(maj, min, str); \
|
||||
#define HCOMMON_ERROR(maj, min, ...) \
|
||||
HERROR(maj, min, __VA_ARGS__); \
|
||||
err_occurred = TRUE;
|
||||
|
||||
/*
|
||||
@ -51,8 +51,8 @@ typedef struct H5E_t H5E_t;
|
||||
* (This macro can also be used to push an error and set the return value
|
||||
* without jumping to any labels)
|
||||
*/
|
||||
#define HDONE_ERROR(maj, min, ret_val, str) { \
|
||||
HCOMMON_ERROR(maj, min, str); \
|
||||
#define HDONE_ERROR(maj, min, ret_val, ...) { \
|
||||
HCOMMON_ERROR(maj, min, __VA_ARGS__); \
|
||||
ret_value = ret_val; \
|
||||
}
|
||||
|
||||
@ -63,8 +63,8 @@ typedef struct H5E_t H5E_t;
|
||||
* error string. The return value is assigned to a variable `ret_value' and
|
||||
* control branches to the `done' label.
|
||||
*/
|
||||
#define HGOTO_ERROR(maj, min, ret_val, str) { \
|
||||
HCOMMON_ERROR(maj, min, str); \
|
||||
#define HGOTO_ERROR(maj, min, ret_val, ...) { \
|
||||
HCOMMON_ERROR(maj, min, __VA_ARGS__); \
|
||||
HGOTO_DONE(ret_val) \
|
||||
}
|
||||
|
||||
|
@ -732,11 +732,11 @@ H5FD_sec2_read(H5FD_t *_file, H5FD_mem_t UNUSED type, hid_t UNUSED dxpl_id,
|
||||
|
||||
/* Check for overflow conditions */
|
||||
if(!H5F_addr_defined(addr))
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "addr undefined")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "addr undefined, addr = %llu", (unsigned long long)addr)
|
||||
if(REGION_OVERFLOW(addr, size))
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow, addr = %llu", (unsigned long long)addr)
|
||||
if((addr + size) > file->eoa)
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow, addr = %llu", (unsigned long long)addr)
|
||||
|
||||
/* Seek to the correct location */
|
||||
if((addr != file->pos || OP_READ != file->op) &&
|
||||
@ -813,11 +813,11 @@ H5FD_sec2_write(H5FD_t *_file, H5FD_mem_t UNUSED type, hid_t UNUSED dxpl_id, had
|
||||
|
||||
/* Check for overflow conditions */
|
||||
if(!H5F_addr_defined(addr))
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "addr undefined")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "addr undefined, addr = %llu", (unsigned long long)addr)
|
||||
if(REGION_OVERFLOW(addr, size))
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow, addr = %llu", (unsigned long long)addr)
|
||||
if((addr + size) > file->eoa)
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow")
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_OVERFLOW, FAIL, "addr overflow, addr = %llu", (unsigned long long)addr)
|
||||
|
||||
/* Seek to the correct location */
|
||||
if((addr != file->pos || OP_WRITE != file->op) &&
|
||||
|
@ -890,7 +890,7 @@ done:
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
static herr_t
|
||||
H5G_get_objinfo_cb(H5G_loc_t *grp_loc/*in*/, const char UNUSED *name, const H5O_link_t *lnk,
|
||||
H5G_get_objinfo_cb(H5G_loc_t *grp_loc/*in*/, const char *name, const H5O_link_t *lnk,
|
||||
H5G_loc_t *obj_loc, void *_udata/*in,out*/, H5G_own_loc_t *own_loc/*out*/)
|
||||
{
|
||||
H5G_trav_goi_t *udata = (H5G_trav_goi_t *)_udata; /* User data passed in */
|
||||
@ -900,7 +900,7 @@ H5G_get_objinfo_cb(H5G_loc_t *grp_loc/*in*/, const char UNUSED *name, const H5O_
|
||||
|
||||
/* Check if the name in this group resolved to a valid link */
|
||||
if(lnk == NULL && obj_loc == NULL)
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "name doesn't exist")
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "'%s' doesn't exist", name)
|
||||
|
||||
/* Only modify user's buffer if it's available */
|
||||
if(udata->statbuf) {
|
||||
|
@ -716,7 +716,7 @@ H5Lget_val(hid_t loc_id, const char *name, void *buf/*out*/, size_t size,
|
||||
|
||||
/* Get the link value */
|
||||
if(H5L_get_val(&loc, name, buf, size, lapl_id, H5AC_ind_dxpl_id) < 0)
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "unable to get link value")
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "unable to get link value for '%s'", name)
|
||||
|
||||
done:
|
||||
FUNC_LEAVE_API(ret_value)
|
||||
@ -2120,7 +2120,7 @@ done:
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
static herr_t
|
||||
H5L_get_val_cb(H5G_loc_t UNUSED *grp_loc/*in*/, const char UNUSED *name, const H5O_link_t *lnk,
|
||||
H5L_get_val_cb(H5G_loc_t UNUSED *grp_loc/*in*/, const char *name, const H5O_link_t *lnk,
|
||||
H5G_loc_t UNUSED *obj_loc, void *_udata/*in,out*/, H5G_own_loc_t *own_loc/*out*/)
|
||||
{
|
||||
H5L_trav_gv_t *udata = (H5L_trav_gv_t *)_udata; /* User data passed in */
|
||||
@ -2130,7 +2130,7 @@ H5L_get_val_cb(H5G_loc_t UNUSED *grp_loc/*in*/, const char UNUSED *name, const H
|
||||
|
||||
/* Check if the name in this group resolved to a valid link */
|
||||
if(lnk == NULL)
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "name doesn't exist")
|
||||
HGOTO_ERROR(H5E_SYM, H5E_NOTFOUND, FAIL, "'%s' doesn't exist", name)
|
||||
|
||||
/* Retrieve the value for the link */
|
||||
if(H5L_get_val_real(lnk, udata->buf, udata->size) < 0)
|
||||
|
@ -514,6 +514,7 @@ H5Lcreate_external(const char *file_name, const char *obj_name,
|
||||
hid_t link_loc_id, const char *link_name, hid_t lcpl_id, hid_t lapl_id)
|
||||
{
|
||||
H5G_loc_t link_loc; /* Group location to create link */
|
||||
char *norm_obj_name = NULL; /* Pointer to normalized current name */
|
||||
void *ext_link_buf = NULL; /* Buffer to contain external link */
|
||||
size_t buf_size; /* Size of buffer to hold external link */
|
||||
uint8_t *p; /* Pointer into external link buffer */
|
||||
@ -533,8 +534,12 @@ H5Lcreate_external(const char *file_name, const char *obj_name,
|
||||
if(!link_name || !*link_name)
|
||||
HGOTO_ERROR(H5E_ARGS, H5E_BADVALUE, FAIL, "no link name specified")
|
||||
|
||||
/* Get normalized copy of the link target */
|
||||
if(NULL == (norm_obj_name = H5G_normalize(obj_name)))
|
||||
HGOTO_ERROR(H5E_SYM, H5E_BADVALUE, FAIL, "can't normalize object name")
|
||||
|
||||
/* Combine the filename and link name into a single buffer to give to the UD link */
|
||||
buf_size = 1 + (HDstrlen(file_name) + 1) + (HDstrlen(obj_name) + 1);
|
||||
buf_size = 1 + (HDstrlen(file_name) + 1) + (HDstrlen(norm_obj_name) + 1);
|
||||
if(NULL == (ext_link_buf = H5MM_malloc(buf_size)))
|
||||
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "unable to allocate udata buffer")
|
||||
|
||||
@ -543,14 +548,14 @@ H5Lcreate_external(const char *file_name, const char *obj_name,
|
||||
*p++ = (H5L_EXT_VERSION << 4) | H5L_EXT_FLAGS_ALL; /* External link version & flags */
|
||||
HDstrcpy((char *)p, file_name); /* Name of file containing external link's object */
|
||||
p += HDstrlen(file_name) + 1;
|
||||
HDstrcpy((char *)p, obj_name); /* External link's object */
|
||||
HDstrcpy((char *)p, norm_obj_name); /* External link's object */
|
||||
|
||||
/* Create an external link */
|
||||
if(H5L_create_ud(&link_loc, link_name, ext_link_buf, buf_size, H5L_TYPE_EXTERNAL, lcpl_id, lapl_id, H5AC_dxpl_id) < 0)
|
||||
HGOTO_ERROR(H5E_LINK, H5E_CANTINIT, FAIL, "unable to create link")
|
||||
|
||||
done:
|
||||
if(ext_link_buf != NULL)
|
||||
if(norm_obj_name)
|
||||
H5MM_free(ext_link_buf);
|
||||
|
||||
FUNC_LEAVE_API(ret_value)
|
||||
|
47
test/links.c
47
test/links.c
@ -1794,6 +1794,30 @@ external_link_root(hid_t fapl, hbool_t new_format)
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* Create external link to object in first file */
|
||||
/* (add a few extra '/'s to make certain library normalizes external link object names) */
|
||||
if(H5Lcreate_external(filename1, "///", fid, "ext_link2", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
|
||||
/* Check information for external link */
|
||||
if(H5Lget_info(fid, "ext_link", &linfo, H5P_DEFAULT) < 0) goto error;
|
||||
if(H5L_TYPE_EXTERNAL != linfo.type) {
|
||||
H5_FAILED();
|
||||
puts(" Unexpected object type - should have been an external link");
|
||||
goto error;
|
||||
}
|
||||
if(H5Lget_val(fid, "ext_link", objname, sizeof(objname), H5P_DEFAULT) < 0) TEST_ERROR
|
||||
if(H5Lunpack_elink_val(objname, linfo.u.val_size, NULL, &file, &path) < 0) TEST_ERROR
|
||||
if(HDstrcmp(file, filename1)) {
|
||||
H5_FAILED();
|
||||
puts(" External link file name incorrect");
|
||||
goto error;
|
||||
}
|
||||
if(HDstrcmp(path, "/")) {
|
||||
H5_FAILED();
|
||||
puts(" External link path incorrect");
|
||||
goto error;
|
||||
}
|
||||
|
||||
/* Close and re-open file to ensure that data is written to disk */
|
||||
if(H5Fclose(fid) < 0) TEST_ERROR
|
||||
if((fid = H5Fopen(filename2, H5F_ACC_RDWR, fapl)) < 0) TEST_ERROR
|
||||
@ -3411,8 +3435,8 @@ external_link_reltar(hid_t fapl, hbool_t new_format)
|
||||
h5_fixname(FILENAME[26], fapl, filename2, sizeof filename2);
|
||||
|
||||
/* Create the target file */
|
||||
if((fid=H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
|
||||
if((gid=H5Gcreate2(fid, "A", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
|
||||
if((fid = H5Fcreate(filename2, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
|
||||
if((gid = H5Gcreate2(fid, "A", H5P_DEFAULT, H5P_DEFAULT, H5P_DEFAULT)) < 0) TEST_ERROR
|
||||
|
||||
/* closing for target file */
|
||||
if(H5Gclose(gid) < 0) TEST_ERROR
|
||||
@ -3420,25 +3444,17 @@ external_link_reltar(hid_t fapl, hbool_t new_format)
|
||||
|
||||
|
||||
/* Create the main file */
|
||||
if((fid=H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
|
||||
if((fid = H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
|
||||
|
||||
/* Create external link to target file */
|
||||
if(H5Lcreate_external(filename2, "/A", fid, "ext_link", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
if(H5Lcreate_external(filename2, "///A", fid, "ext_link", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
|
||||
/* Open object through external link */
|
||||
H5E_BEGIN_TRY {
|
||||
gid = H5Gopen2(fid, "ext_link", H5P_DEFAULT);
|
||||
} H5E_END_TRY;
|
||||
|
||||
/*
|
||||
* Should be able to find the target file from:
|
||||
* main file's current working directory + pathname of external linked targetfile
|
||||
*/
|
||||
if (gid < 0) {
|
||||
if((gid = H5Gopen2(fid, "ext_link", H5P_DEFAULT)) < 0) {
|
||||
H5_FAILED();
|
||||
puts(" Should have found the file in tmp directory.");
|
||||
goto error;
|
||||
}
|
||||
} /* end if */
|
||||
|
||||
/* closing for main file */
|
||||
if(H5Gclose(gid) < 0) TEST_ERROR
|
||||
@ -5301,7 +5317,8 @@ external_link_query(hid_t fapl, hbool_t new_format)
|
||||
if((fid=H5Fcreate(filename1, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0) TEST_ERROR
|
||||
|
||||
/* Create external link */
|
||||
if(H5Lcreate_external(filename2, "/dst", fid, "src", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
/* (add a few extra '/'s to make certain library normalizes external link object names) */
|
||||
if(H5Lcreate_external(filename2, "///dst//", fid, "src", H5P_DEFAULT, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
|
||||
/* Get size of buffer for external link */
|
||||
if(H5Lget_info(fid, "src", &li, H5P_DEFAULT) < 0) TEST_ERROR
|
||||
|
Loading…
x
Reference in New Issue
Block a user