mirror of
https://github.com/HDFGroup/hdf5.git
synced 2024-11-21 01:04:10 +08:00
[svn-r14083] Description:
Correct problem with fractal heap's free space size usage gathering routine, which was "poisoning the cache" by loading an incorrectly initialized piece of metadata from the file. Tested on: FreeBSD/32 6.2 (duty) Mac OS X/32 6.2 (amazon)
This commit is contained in:
parent
abd36a6f6e
commit
4dc989f282
29
src/H5FS.c
29
src/H5FS.c
@ -167,7 +167,7 @@ H5FS_open(H5F_t *f, hid_t dxpl_id, haddr_t fs_addr, size_t nclasses,
|
||||
|
||||
FUNC_ENTER_NOAPI(H5FS_open, NULL)
|
||||
#ifdef QAK
|
||||
HDfprintf(stderr, "%s: Opening free space manager\n", FUNC);
|
||||
HDfprintf(stderr, "%s: Opening free space manager, nclasses = %Zu\n", FUNC, nclasses);
|
||||
#endif /* QAK */
|
||||
|
||||
/* Check arguments. */
|
||||
@ -467,40 +467,21 @@ done:
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
herr_t
|
||||
H5FS_size(H5F_t *f, hid_t dxpl_id, haddr_t fs_addr, hsize_t *meta_size)
|
||||
H5FS_size(const H5F_t *f, const H5FS_t *fspace, hsize_t *meta_size)
|
||||
{
|
||||
H5FS_t *fspace = NULL; /* Free space header info */
|
||||
H5FS_prot_t fs_prot; /* Information for protecting free space manager */
|
||||
herr_t ret_value = SUCCEED; /* Return value */
|
||||
|
||||
FUNC_ENTER_NOAPI(H5FS_size, FAIL)
|
||||
FUNC_ENTER_NOAPI_NOFUNC(H5FS_size)
|
||||
|
||||
/*
|
||||
* Check arguments.
|
||||
*/
|
||||
HDassert(f);
|
||||
HDassert(H5F_addr_defined(fs_addr));
|
||||
HDassert(fspace);
|
||||
HDassert(meta_size);
|
||||
|
||||
/* Initialize user data for protecting the free space manager */
|
||||
fs_prot.nclasses = 0;
|
||||
fs_prot.classes = NULL;
|
||||
fs_prot.cls_init_udata = NULL;
|
||||
|
||||
/*
|
||||
* Load the free space header.
|
||||
*/
|
||||
if(NULL == (fspace = H5AC_protect(f, dxpl_id, H5AC_FSPACE_HDR, fs_addr, &fs_prot, NULL, H5AC_READ)))
|
||||
HGOTO_ERROR(H5E_FSPACE, H5E_CANTLOAD, FAIL, "unable to load free space header")
|
||||
|
||||
/* Get the free space size info */
|
||||
*meta_size += H5FS_HEADER_SIZE(f) + fspace->alloc_sect_size;
|
||||
|
||||
done:
|
||||
if(fspace && H5AC_unprotect(f, dxpl_id, H5AC_FSPACE_HDR, fs_addr, fspace, H5AC__NO_FLAGS_SET) < 0)
|
||||
HDONE_ERROR(H5E_FSPACE, H5E_PROTECT, FAIL, "unable to release free space header")
|
||||
|
||||
FUNC_LEAVE_NOAPI(ret_value)
|
||||
FUNC_LEAVE_NOAPI(SUCCEED)
|
||||
} /* end H5FS_size() */
|
||||
|
||||
#ifdef H5FS_DEBUG
|
||||
|
@ -158,8 +158,7 @@ H5_DLL H5FS_t *H5FS_create(H5F_t *f, hid_t dxpl_id, haddr_t *fs_addr,
|
||||
const H5FS_section_class_t *classes[], void *cls_init_udata);
|
||||
H5_DLL H5FS_t *H5FS_open(H5F_t *f, hid_t dxpl_id, haddr_t fs_addr,
|
||||
size_t nclasses, const H5FS_section_class_t *classes[], void *cls_init_udata);
|
||||
H5_DLL herr_t H5FS_size(H5F_t *f, hid_t dxpl_id, haddr_t fs_addr,
|
||||
hsize_t *meta_size);
|
||||
H5_DLL herr_t H5FS_size(const H5F_t *f, const H5FS_t *fspace, hsize_t *meta_size);
|
||||
H5_DLL herr_t H5FS_delete(H5F_t *f, hid_t dxpl_id, haddr_t fs_addr);
|
||||
H5_DLL herr_t H5FS_close(H5F_t *f, hid_t dxpl_id, H5FS_t *fspace);
|
||||
|
||||
|
@ -1205,6 +1205,7 @@ HDfprintf(stderr, "%s: request = %Hu\n", FUNC, request);
|
||||
|
||||
/* Check arguments. */
|
||||
HDassert(fspace);
|
||||
HDassert(fspace->nclasses);
|
||||
HDassert(request);
|
||||
HDassert(node);
|
||||
|
||||
|
@ -697,6 +697,7 @@ H5_DLL herr_t H5HF_space_add(H5HF_hdr_t *hdr, hid_t dxpl_id,
|
||||
H5HF_free_section_t *node, unsigned flags);
|
||||
H5_DLL htri_t H5HF_space_find(H5HF_hdr_t *hdr, hid_t dxpl_id, hsize_t request,
|
||||
H5HF_free_section_t **node);
|
||||
H5_DLL herr_t H5HF_space_size(H5HF_hdr_t *hdr, hid_t dxpl_id, hsize_t *fs_size);
|
||||
H5_DLL herr_t H5HF_space_remove(H5HF_hdr_t *hdr, hid_t dxpl_id,
|
||||
H5HF_free_section_t *node);
|
||||
H5_DLL herr_t H5HF_space_close(H5HF_hdr_t *hdr, hid_t dxpl_id);
|
||||
|
@ -232,6 +232,47 @@ done:
|
||||
FUNC_LEAVE_NOAPI(ret_value)
|
||||
} /* end H5HF_space_find() */
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Function: H5HF_space_size
|
||||
*
|
||||
* Purpose: Query the size of the heap's free space info on disk
|
||||
*
|
||||
* Return: Success: non-negative
|
||||
* Failure: negative
|
||||
*
|
||||
* Programmer: Quincey Koziol
|
||||
* koziol@hdfgroup.org
|
||||
* August 14 2007
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
herr_t
|
||||
H5HF_space_size(H5HF_hdr_t *hdr, hid_t dxpl_id, hsize_t *fs_size)
|
||||
{
|
||||
herr_t ret_value = SUCCEED; /* Return value */
|
||||
|
||||
FUNC_ENTER_NOAPI_NOINIT(H5HF_space_size)
|
||||
|
||||
/*
|
||||
* Check arguments.
|
||||
*/
|
||||
HDassert(hdr);
|
||||
HDassert(fs_size);
|
||||
|
||||
/* Check if the free space for the heap has been initialized */
|
||||
if(!hdr->fspace)
|
||||
if(H5HF_space_start(hdr, dxpl_id) < 0)
|
||||
HGOTO_ERROR(H5E_HEAP, H5E_CANTINIT, FAIL, "can't initialize heap free space")
|
||||
|
||||
/* Get free space metadata size */
|
||||
if(H5FS_size(hdr->f, hdr->fspace, fs_size) < 0)
|
||||
HGOTO_ERROR(H5E_FSPACE, H5E_CANTGET, FAIL, "can't retrieve FS meta storage info")
|
||||
|
||||
done:
|
||||
FUNC_LEAVE_NOAPI(ret_value)
|
||||
} /* end H5HF_space_size() */
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Function: H5HF_space_remove
|
||||
|
@ -175,7 +175,7 @@ H5HF_size(H5F_t *f, hid_t dxpl_id, haddr_t fh_addr, hsize_t *heap_size)
|
||||
|
||||
/* Get storage for free-space tracking info */
|
||||
if(H5F_addr_defined(hdr->fs_addr))
|
||||
if(H5FS_size(f, dxpl_id, hdr->fs_addr, heap_size) < 0)
|
||||
if(H5HF_space_size(hdr, dxpl_id, heap_size) < 0)
|
||||
HGOTO_ERROR(H5E_FSPACE, H5E_CANTGET, FAIL, "can't retrieve FS meta storage info")
|
||||
|
||||
done:
|
||||
|
141
test/fheap.c
141
test/fheap.c
@ -2744,6 +2744,146 @@ error:
|
||||
return(1);
|
||||
} /* test_filtered_create() */
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
* Function: test_size
|
||||
*
|
||||
* Purpose: Test querying heap size
|
||||
*
|
||||
* Return: Success: 0
|
||||
* Failure: 1
|
||||
*
|
||||
* Programmer: Quincey Koziol
|
||||
* Tuesday, August 14, 2007
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
static int
|
||||
test_size(hid_t fapl, H5HF_create_t *cparam)
|
||||
{
|
||||
hid_t file = -1; /* File ID */
|
||||
hid_t dxpl = H5P_DATASET_XFER_DEFAULT; /* DXPL to use */
|
||||
char filename[FHEAP_FILENAME_LEN]; /* Filename to use */
|
||||
H5F_t *f = NULL; /* Internal file object pointer */
|
||||
H5HF_t *fh = NULL; /* Fractal heap wrapper */
|
||||
haddr_t fh_addr; /* Address of fractal heap */
|
||||
hsize_t empty_heap_size; /* Total size of empty heap on disk */
|
||||
hsize_t one_heap_size; /* Total size of heap on disk after inserting one object */
|
||||
hsize_t heap_size; /* Total size of heap on disk */
|
||||
|
||||
/* Set the filename to use for this test (dependent on fapl) */
|
||||
h5_fixname(FILENAME[0], fapl, filename, sizeof(filename));
|
||||
|
||||
/* Create the file to work on */
|
||||
if((file = H5Fcreate(filename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Get a pointer to the internal file object */
|
||||
if(NULL == (f = H5I_object(file)))
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Display testing message */
|
||||
TESTING("querying heap statistics")
|
||||
|
||||
|
||||
/* Create absolute heap */
|
||||
if(NULL == (fh = H5HF_create(f, dxpl, cparam)))
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Get heap's address */
|
||||
if(H5HF_get_heap_addr(fh, &fh_addr) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(!H5F_addr_defined(fh_addr))
|
||||
TEST_ERROR
|
||||
|
||||
/* Get an empty heap's size */
|
||||
empty_heap_size = 0;
|
||||
if(H5HF_size(f, dxpl, fh_addr, &empty_heap_size) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(empty_heap_size == 0)
|
||||
TEST_ERROR
|
||||
|
||||
/* Insert an object */
|
||||
if(add_obj(fh, dxpl, (size_t)0, (size_t)10, NULL, NULL) < 0)
|
||||
TEST_ERROR
|
||||
|
||||
/* Get the heap's size after inserting one object */
|
||||
one_heap_size = 0;
|
||||
if(H5HF_size(f, dxpl, fh_addr, &one_heap_size) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(one_heap_size <= empty_heap_size)
|
||||
TEST_ERROR
|
||||
|
||||
/* Close the fractal heap */
|
||||
if(H5HF_close(fh, dxpl) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
fh = NULL;
|
||||
|
||||
/* Close the file */
|
||||
if(H5Fclose(file) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
|
||||
/* Re-open the file */
|
||||
if((file = H5Fopen(filename, H5F_ACC_RDWR, fapl)) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Get a pointer to the internal file object */
|
||||
if(NULL == (f = H5I_object(file)))
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Check the heap's size */
|
||||
heap_size = 0;
|
||||
if(H5HF_size(f, dxpl, fh_addr, &heap_size) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(heap_size != one_heap_size)
|
||||
TEST_ERROR
|
||||
|
||||
/* Re-open the heap */
|
||||
if(NULL == (fh = H5HF_open(f, H5P_DATASET_XFER_DEFAULT, fh_addr)))
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* Check the heap's size */
|
||||
heap_size = 0;
|
||||
if(H5HF_size(f, dxpl, fh_addr, &heap_size) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(heap_size != one_heap_size)
|
||||
TEST_ERROR
|
||||
|
||||
/* Insert another object */
|
||||
if(add_obj(fh, dxpl, (size_t)1, (size_t)10, NULL, NULL) < 0)
|
||||
TEST_ERROR
|
||||
|
||||
/* Check the heap's size */
|
||||
heap_size = 0;
|
||||
if(H5HF_size(f, dxpl, fh_addr, &heap_size) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
if(heap_size != one_heap_size)
|
||||
TEST_ERROR
|
||||
|
||||
/* Close the fractal heap */
|
||||
if(H5HF_close(fh, H5P_DATASET_XFER_DEFAULT) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
|
||||
/* Close the file */
|
||||
if(H5Fclose(file) < 0)
|
||||
FAIL_STACK_ERROR
|
||||
|
||||
/* All tests passed */
|
||||
PASSED()
|
||||
|
||||
return(0);
|
||||
|
||||
error:
|
||||
H5E_BEGIN_TRY {
|
||||
if(fh)
|
||||
H5HF_close(fh, dxpl);
|
||||
H5Fclose(file);
|
||||
} H5E_END_TRY;
|
||||
return(1);
|
||||
} /* test_size() */
|
||||
|
||||
#ifndef QAK2
|
||||
|
||||
/*-------------------------------------------------------------------------
|
||||
@ -15622,6 +15762,7 @@ curr_test = FHEAP_TEST_NORMAL;
|
||||
nerrors += test_delete_open(fapl, &small_cparam, &tparam);
|
||||
nerrors += test_id_limits(fapl, &small_cparam);
|
||||
nerrors += test_filtered_create(fapl, &small_cparam);
|
||||
nerrors += test_size(fapl, &small_cparam);
|
||||
|
||||
#ifndef QAK2
|
||||
#ifndef QAK
|
||||
|
Loading…
Reference in New Issue
Block a user