hdf5/test/freespace.c
David Young 307cb5da48 Squash my changes on branch fprintf-experiment into one commit for
reapplication to my new warnings branch, `warnings-again`.  These
changes are included:

commit 915551b7bf64e777dd2007386ec77b1d117770da
Merge: 63858c2 a8892bb
Author: David Young <dyoung@hdfgroup.org>
Date:   Mon Nov 25 17:39:49 2019 -0600

    Merge remote-tracking branch 'hdf5/develop' into fprintf-experiment

commit a8892bb42d
Merge: 5c911d8 f907b51
Author: David Young <dyoung@hdfgroup.org>
Date:   Mon Nov 25 17:33:54 2019 -0600

    Merge pull request #2055 in HDFFV/hdf5 from ~DYOUNG/vchoi_fork:add-werror-and-squash-some to develop

    * commit 'f907b511d06612dafc7814a7c30f2f3d2b76d52b':
      Oops, remove more C99 designated initializers for VS 2010 compatibility.

commit 63858c22e168acaec0af8ced6641f26102cc6bb0
Merge: 20ae787 5c911d8
Author: David Young <dyoung@hdfgroup.org>
Date:   Mon Nov 25 17:04:42 2019 -0600

    Merge remote-tracking branch 'hdf5/develop' into fprintf-experiment

commit 5c911d8baf
Merge: b8a5671 62208b0
Author: David Young <dyoung@hdfgroup.org>
Date:   Mon Nov 25 16:58:27 2019 -0600

    Merge pull request #2030 in HDFFV/hdf5 from ~DYOUNG/vchoi_fork:add-werror-and-squash-some to develop

    * commit '62208b056a09c01855fbac7f75146be58ad6bfe5': (44 commits)
      Add an #include to get a function declaration.
      Don't use C99 designated initializers, they're not compatible with Visual Studio 2010.
      Quiet some more maybe-uninitialized warnings---each is a false positive, *sigh*.  This is more code that may not compile with VS2010, *sigh sigh*.
      Always warn on maybe-uninitialized.  -Wincompatible-pointer-types was not available until GCC 5, so enable it only if that's the GCC version we're using.
      Only promote maybe-uninitialized warnings to errors on GCC 8.  Even on GCC 8, there may be false positives at low optimization levels?  I need to check.
      Only use -Werror=cast-function-type with GCC 8 and later.
      Put all of the -W options back into the order I found them in so that it's easier to compare old and new config/gnu-flags.
      Add new source files to CMakeLists.txt.
      Mention the -Werror= flags in libhdf5.settings.in.
      free -> HDfree
      Promote decleration-after-statement warnings to errors.
      Quiet decleration-after-statement warnings.
      Move a statement under some declarations since some vintages of Visual Studio don't like declarations after statements.
      Document H5D__chunk_mem_xfree_wrapper().
      Undo accidental test deletion.
      Oops, delete a debug printf that snuck in here.
      Undo my changes to the HD macros, hadn't really intended those to be on this branch....
      Make errors of some more warnings.  Move disabled warnings to DEVELOPER_WARNING_CFLAGS.  Put just one warning option on a line, and sort some of the options.
      Cast to the parameter type, H5VL_token_t *, instead of to unsigned char *.
      Change hdset_reg_ref_t and H5R_ref_t from arrays of unsigned char to structs containing those arrays.  Encapsulating the arrays in this way makes it easier to write and think about pointers to these types, casts to/from these types, etc.
      ...

commit 20ae7877e33931b95e8c3502b027d6c3fe94a11f
Merge: 46f8c61 edd5297
Author: David Young <dyoung@hdfgroup.org>
Date:   Fri Nov 22 15:34:09 2019 -0600

    Merge remote-tracking branch 'origin/add-werror-and-squash-some' into fprintf-experiment

commit 46f8c613d5117a8be5bc8385a072daa0b4262f06
Author: David Young <dyoung@hdfgroup.org>
Date:   Fri Nov 22 15:29:00 2019 -0600

    GCC really wants us to use `ll` to format `long long`, so try to make that work
    before any other format modifier.  Seems like we're not compiling the autoconf
    test program with -Werror=format ?  Probably should.

commit eee35b8ef3759c391327cd48a9b3c56b6f8abc99
Author: David Young <dyoung@hdfgroup.org>
Date:   Fri Nov 22 15:28:05 2019 -0600

    It's hard to know just how wide an HDoff_t will be, and I don't think POSIX or
    C standards provide a PRI macro for it, so cast to intmax_t and format using
    PRIdMAX.

commit 86eab12df7a89b546a38e99f8178dd2adbcb3433
Author: David Young <dyoung@hdfgroup.org>
Date:   Fri Nov 22 15:26:25 2019 -0600

    URemove some casts.se the right format string for the argument.  Here and there
    stop casting a printf argument.

commit f722f7cbecbaa99449941484b014426f62f1bed5
Merge: 58e3743 6d5ec83
Author: David Young <dyoung@hdfgroup.org>
Date:   Fri Nov 22 14:44:16 2019 -0600

    Merge branch 'add-werror-and-squash-some' into fprintf-experiment

commit 58e3743b7faa9836606ee91798fe80dfc0040da7
Author: David Young <dyoung@hdfgroup.org>
Date:   Wed Nov 20 21:07:21 2019 -0600

    Remove custom HDfprintf implementation, using the standard library's,
    instead.  Take a swipe at repairing fprintf format strings, mainly
    replacing "%Hu" with "%" PRIuHSIZE, "%a" with "%" PRIuHADDR, "%Zu" with
    "%zu".

    Here and there remove an awkward cast of a printf argument to `long
    long` and use PRI[doux]8, PRI[doux]32, or PRI[doux]64, instead.

    Change occurrences of "%t" to "%s" and perform a suitable change of
    argument, `cond` -> `cond ? "TRUE" : "FALSE"`.

    Some occurrences of %Hu, %a, and %t remain, they just weren't flagged by
    the compiler because of #ifdef'age.

commit d4366909293fa970c23512ac80e5d865d76cddbf
Author: David Young <dyoung@hdfgroup.org>
Date:   Wed Nov 20 20:54:32 2019 -0600

    Promote format-string warnigns to errors.
2020-07-07 10:49:55 -05:00

2918 lines
89 KiB
C

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
* Copyright by The HDF Group. *
* Copyright by the Board of Trustees of the University of Illinois. *
* All rights reserved. *
* *
* This file is part of HDF5. The full HDF5 copyright notice, including *
* terms governing use, modification, and redistribution, is contained in *
* the COPYING file, which can be found at the root of the source code *
* distribution tree, or in https://support.hdfgroup.org/ftp/HDF5/releases. *
* If you do not have access to either file, you may request a copy from *
* help@hdfgroup.org. *
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
/*
* Tests for free-space manager
*/
#include "h5test.h"
#define H5FS_FRIEND /*suppress error about including H5FSpkg */
#define H5FS_TESTING
#include "H5FSpkg.h" /* Free space manager */
/* Other private headers that this test requires */
#define H5F_FRIEND /*suppress error about including H5Fpkg */
#include "H5Fpkg.h"
#include "H5CXprivate.h" /* API Contexts */
#include "H5Iprivate.h"
#include "H5VLprivate.h" /* Virtual Object Layer */
#include "H5VMprivate.h"
#define FILENAME_LEN 1024
#define TEST_FSPACE_SECT_TYPE 0
#define TEST_FSPACE_SECT_TYPE_NEW 1
#define TEST_FSPACE_SECT_TYPE_NONE 2
#define TEST_FSPACE_SHRINK 80
#define TEST_FSPACE_EXPAND 120
#define TEST_MAX_SECT_SIZE (64 * 1024)
#define TEST_MAX_INDEX 32
#define TEST_SECT_ADDR60 60
#define TEST_SECT_ADDR70 70
#define TEST_SECT_ADDR80 80
#define TEST_SECT_ADDR100 100
#define TEST_SECT_ADDR150 150
#define TEST_SECT_ADDR200 200
#define TEST_SECT_ADDR300 300
#define TEST_SECT_SIZE5 5
#define TEST_SECT_SIZE10 10
#define TEST_SECT_SIZE15 15
#define TEST_SECT_SIZE20 20
#define TEST_SECT_SIZE30 30
#define TEST_SECT_SIZE40 40
#define TEST_SECT_SIZE50 50
#define TEST_SECT_SIZE80 80
#define FSPACE_THRHD_DEF 1 /* Default: no alignment threshold */
#define FSPACE_ALIGN_DEF 1 /* Default: no alignment */
const char *FILENAME[] = {
"frspace",
NULL
};
typedef struct frspace_state_t {
hsize_t tot_space; /* Total amount of space tracked */
hsize_t tot_sect_count; /* Total # of sections tracked */
hsize_t serial_sect_count; /* # of serializable sections tracked */
hsize_t ghost_sect_count; /* # of un-serializable sections tracked */
} frspace_state_t;
haddr_t g_eoa=0;
static haddr_t TEST_get_eoa(void);
static void TEST_set_eoa(haddr_t);
/*
* TEST client
*/
typedef struct TEST_free_section_t {
H5FS_section_info_t sect_info; /* Free space section information (must be first in struct) */
} TEST_free_section_t;
static herr_t TEST_sect_init_cls(H5FS_section_class_t *, void *);
static herr_t TEST_sect_free(H5FS_section_info_t *_sect);
static herr_t TEST_sect_can_merge(const H5FS_section_info_t *, const H5FS_section_info_t *, void H5_ATTR_UNUSED *);
static herr_t TEST_sect_merging(H5FS_section_info_t **, H5FS_section_info_t *, void H5_ATTR_UNUSED *);
static herr_t TEST_sect_can_shrink(const H5FS_section_info_t *, void *);
static herr_t TEST_sect_shrinking(H5FS_section_info_t **, void *);
static unsigned test_fs_create(hid_t fapl);
static unsigned test_fs_sect_add(hid_t fapl);
static unsigned test_fs_sect_merge(hid_t fapl);
static unsigned test_fs_sect_shrink(hid_t fapl);
static unsigned test_fs_sect_find(hid_t fapl);
static unsigned test_fs_sect_change_class(hid_t fapl);
static unsigned test_fs_sect_extend(hid_t fapl);
static unsigned test_fs_sect_iterate(hid_t fapl);
H5FS_section_class_t TEST_FSPACE_SECT_CLS[1] = {{
TEST_FSPACE_SECT_TYPE, /* Section type */
0, /* Extra serialized size */
H5FS_CLS_MERGE_SYM | H5FS_CLS_ADJUST_OK, /* Class flags */
NULL, /* Class private info */
/* Class methods */
TEST_sect_init_cls, /* Initialize section class */
NULL, /* Terminate section class */
/* Object methods */
NULL, /* Add section */
NULL, /* Serialize section */
NULL, /* Deserialize section */
TEST_sect_can_merge, /* Can sections merge? */
TEST_sect_merging, /* Merge sections */
TEST_sect_can_shrink, /* Can section shrink container?*/
TEST_sect_shrinking, /* Shrink container w/section */
TEST_sect_free, /* Free section */
NULL, /* Check validity of section */
NULL, /* Split section node for alignment */
NULL, /* Dump debugging for section */
}};
H5FS_section_class_t TEST_FSPACE_SECT_CLS_NEW[1] = {{
TEST_FSPACE_SECT_TYPE_NEW, /* Section type */
0, /* Extra serialized size */
H5FS_CLS_MERGE_SYM | H5FS_CLS_ADJUST_OK, /* Class flags */
NULL, /* Class private info */
/* Class methods */
TEST_sect_init_cls, /* Initialize section class */
NULL, /* Terminate section class */
/* Object methods */
NULL, /* Add section */
NULL, /* Serialize section */
NULL, /* Deserialize section */
TEST_sect_can_merge, /* Can sections merge? */
TEST_sect_merging, /* Merge sections */
NULL, /* Can section shrink container?*/
NULL, /* Shrink container w/section */
TEST_sect_free, /* Free section */
NULL, /* Check validity of section */
NULL, /* Split section node for alignment */
NULL, /* Dump debugging for section */
}};
H5FS_section_class_t TEST_FSPACE_SECT_CLS_NOINIT[1] = {{
TEST_FSPACE_SECT_TYPE_NONE, /* Section type */
0, /* Extra serialized size */
H5FS_CLS_MERGE_SYM | H5FS_CLS_ADJUST_OK, /* Class flags */
NULL, /* Class private info */
/* Class methods */
NULL, /* Initialize section class */
NULL, /* Terminate section class */
/* Object methods */
NULL, /* Add section */
NULL, /* Serialize section */
NULL, /* Deserialize section */
TEST_sect_can_merge, /* Can sections merge? */
TEST_sect_merging, /* Merge sections */
NULL, /* Can section shrink container?*/
NULL, /* Shrink container w/section */
TEST_sect_free, /* Free section */
NULL, /* Check validity of section */
NULL, /* Split section node for alignment */
NULL, /* Dump debugging for section */
}};
const H5FS_section_class_t *test_classes[] = {
TEST_FSPACE_SECT_CLS,
TEST_FSPACE_SECT_CLS_NEW,
TEST_FSPACE_SECT_CLS_NOINIT
};
static void init_cparam(H5FS_create_t *);
static void init_sect_node(TEST_free_section_t *, haddr_t, hsize_t, unsigned, H5FS_section_state_t);
static int check_stats(const H5F_t *, const H5FS_t *, frspace_state_t *);
#define NUM_SECTIONS 1000
/* User data for free space section iterator callback */
typedef struct {
hsize_t tot_size;
hsize_t tot_sect_count;
} TEST_iter_ud_t;
static herr_t TEST_sects_cb(H5FS_section_info_t *_sect, void *_udata);
/*
* Tests
*/
/*
* free-space section routines for client TEST
*/
static herr_t
TEST_sect_init_cls(H5FS_section_class_t *cls, void *_udata)
{
herr_t ret_value = SUCCEED; /* Return value */
unsigned *init_flags;
/* Check arguments. */
HDassert(cls);
HDassert(_udata);
init_flags = (unsigned *)_udata;
cls->flags |= *init_flags;
return ret_value;
} /* TEST_sect_init_cls() */
/*
* Check if the two sections can be merged:
* true if second section adjoins the first section
*/
H5_ATTR_PURE static herr_t
TEST_sect_can_merge(const H5FS_section_info_t *_sect1,
const H5FS_section_info_t *_sect2, void H5_ATTR_UNUSED *_udata)
{
const TEST_free_section_t *sect1 = (const TEST_free_section_t *)_sect1;
const TEST_free_section_t *sect2 = (const TEST_free_section_t *)_sect2;
htri_t ret_value; /* Return value */
/* Check arguments. */
HDassert(sect1);
HDassert(sect2);
HDassert(sect1->sect_info.type == sect2->sect_info.type); /* Checks "MERGE_SYM" flag */
HDassert(H5F_addr_lt(sect1->sect_info.addr, sect2->sect_info.addr));
/* Check if second section adjoins first section */
ret_value = H5F_addr_eq(sect1->sect_info.addr + sect1->sect_info.size, sect2->sect_info.addr);
return ret_value;
} /* TEST_sect_can_merge() */
/*
* Merge the two sections (second section is merged into the first section)
*/
static herr_t
TEST_sect_merging(H5FS_section_info_t **_sect1, H5FS_section_info_t *_sect2,
void H5_ATTR_UNUSED *_udata)
{
TEST_free_section_t **sect1 = (TEST_free_section_t **)_sect1;
TEST_free_section_t *sect2 = (TEST_free_section_t *)_sect2;
herr_t ret_value = SUCCEED; /* Return value */
/* Check arguments. */
HDassert(sect1);
HDassert(((*sect1)->sect_info.type == TEST_FSPACE_SECT_TYPE) ||
((*sect1)->sect_info.type == TEST_FSPACE_SECT_TYPE_NEW) ||
((*sect1)->sect_info.type == TEST_FSPACE_SECT_TYPE_NONE));
HDassert(sect2);
HDassert((sect2->sect_info.type == TEST_FSPACE_SECT_TYPE) ||
(sect2->sect_info.type == TEST_FSPACE_SECT_TYPE_NEW) ||
(sect2->sect_info.type == TEST_FSPACE_SECT_TYPE_NONE));
HDassert(H5F_addr_eq((*sect1)->sect_info.addr + (*sect1)->sect_info.size, sect2->sect_info.addr));
/* Add second section's size to first section */
(*sect1)->sect_info.size += sect2->sect_info.size;
/* Get rid of second section */
if(TEST_sect_free((H5FS_section_info_t *)sect2) < 0)
TEST_ERROR
error:
return ret_value;
} /* TEST_sect_merging() */
/*
* Free the section
*/
static herr_t
TEST_sect_free(H5FS_section_info_t *sect)
{
/* Release the section */
HDfree(sect);
return 0;
} /* TEST_sect_free() */
/*
* Determine if the section can be shrunk and set _udata accordingly
* if _udata passed in is NULL, return FALSE
* Otherwise:
* if section's address+size is the end of file, return TRUE
* otherwise return FALSE
*/
static herr_t
TEST_sect_can_shrink(const H5FS_section_info_t *_sect, void *_udata)
{
unsigned *can_shrink = (unsigned *)_udata;
const TEST_free_section_t *sect = (const TEST_free_section_t *)_sect;
haddr_t end, eoa;
if(can_shrink == NULL)
return FALSE;
end = sect->sect_info.addr + sect->sect_info.size;
eoa = TEST_get_eoa();
if (end == eoa)
*can_shrink = TRUE;
else
*can_shrink = FALSE;
return (htri_t)*can_shrink;
} /* TEST_sect_can_shrink() */
/*
* Shrink the section
*/
static herr_t
TEST_sect_shrinking(H5FS_section_info_t **_sect, void *_udata)
{
TEST_free_section_t **sect = (TEST_free_section_t **)_sect;
unsigned *can_shrink = (unsigned *)_udata;
/* address of the section is faked, so, doesn't need to do anything */
/* just free the section node */
if (*can_shrink) {
if (TEST_sect_free((H5FS_section_info_t *)*sect) < 0)
TEST_ERROR
*sect = NULL;
return TRUE;
} /* end if */
error:
return FALSE;
}
/*
* iteration callback
*/
static herr_t
TEST_sects_cb(H5FS_section_info_t *_sect, void *_udata)
{
TEST_free_section_t *sect = (TEST_free_section_t *)_sect;
TEST_iter_ud_t *udata = (TEST_iter_ud_t *)_udata;
herr_t ret_value = SUCCEED; /* Return value */
HDassert(sect);
HDassert(udata);
udata->tot_size += sect->sect_info.size;
udata->tot_sect_count += 1;
return(ret_value);
}
/* supporting routine for shrinking */
static haddr_t
TEST_get_eoa(void)
{
return g_eoa;
}
/* supporting routine for shrinking */
static void
TEST_set_eoa(haddr_t val)
{
g_eoa = val;
}
/*
* Initialize creation parameter structure for TEST client
*/
static void
init_cparam(H5FS_create_t *cparam)
{
HDmemset(cparam, 0, sizeof(H5FS_create_t));
/* Set the free space creation parameters */
cparam->shrink_percent = TEST_FSPACE_SHRINK;
cparam->expand_percent = TEST_FSPACE_EXPAND;
cparam->max_sect_size = TEST_MAX_SECT_SIZE;
cparam->max_sect_addr = TEST_MAX_INDEX;
} /* init_cparam() */
/*
* Initialize free space section node
*/
static void
init_sect_node(TEST_free_section_t *sect_node, haddr_t addr, hsize_t size, unsigned type, H5FS_section_state_t state)
{
sect_node->sect_info.addr = addr;
sect_node->sect_info.size = size;
sect_node->sect_info.type = type;
sect_node->sect_info.state = state;
} /* init_sect_node() */
/*
* Verify statistics for the free-space manager
*/
static int
check_stats(const H5F_t *f, const H5FS_t *frsp, frspace_state_t *state)
{
H5FS_stat_t frspace_stats; /* Statistics about the heap */
/* Get statistics for heap and verify they are correct */
if(H5FS_stat_info(f, frsp, &frspace_stats) < 0)
FAIL_STACK_ERROR
if(frspace_stats.tot_space != state->tot_space) {
HDfprintf(stdout, "frspace_stats.tot_space = %" PRIuHSIZE ", state->tot_space = %" PRIuHSIZE "\n",
frspace_stats.tot_space, state->tot_space);
TEST_ERROR
} /* end if */
if(frspace_stats.tot_sect_count != state->tot_sect_count) {
HDfprintf(stdout, "frspace_stats.tot_sect_count = %" PRIuHSIZE ", state->tot_sect_count = %" PRIuHSIZE "\n",
frspace_stats.tot_sect_count, state->tot_sect_count);
TEST_ERROR
} /* end if */
if(frspace_stats.serial_sect_count != state->serial_sect_count) {
HDfprintf(stdout, "frspace_stats.serial_sect_count = %" PRIuHSIZE ", state->serial_sect_count = %" PRIuHSIZE "\n",
frspace_stats.serial_sect_count, state->serial_sect_count);
TEST_ERROR
} /* end if */
if(frspace_stats.ghost_sect_count != state->ghost_sect_count) {
HDfprintf(stdout, "frspace_stats.ghost_sect_count = %" PRIuHSIZE ", state->ghost_sect_count = %" PRIuHSIZE "\n",
frspace_stats.ghost_sect_count, state->ghost_sect_count);
TEST_ERROR
} /* end if */
/* All tests passed */
return 0;
error:
return 1;
} /* check_stats() */
/*
* TESTS for free-space manager
*/
/*
* To verify the creation, close, reopen and deletion of the free-space manager
*/
static unsigned
test_fs_create(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr; /* address of free space */
h5_stat_size_t file_size, empty_size; /* File size */
frspace_state_t state; /* State of free space*/
H5FS_create_t cparam, test_cparam; /* creation parameters */
uint16_t nclasses;
unsigned init_flags=0;
TESTING("the creation/close/reopen/deletion of the free-space manager");
/* 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
/* Close file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((empty_size = h5_get_file_size(filename, fapl)) < 0)
TEST_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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
/* initialize creation parameters for free-space manager */
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if(frsp->nclasses != nclasses)
TEST_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
if(check_stats(f, frsp, &state))
TEST_ERROR
HDmemset(&test_cparam, 0, sizeof(H5FS_create_t));
if(H5FS__get_cparam_test(frsp, &test_cparam) < 0)
FAIL_STACK_ERROR
if(H5FS__cmp_cparam_test(&cparam, &test_cparam))
FAIL_STACK_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* reopen the free-space manager */
if(NULL == (frsp = H5FS_open(f, fs_addr,
nclasses, test_classes, NULL, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if (frsp->nclasses != nclasses)
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of the file */
if((file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_ERROR
/* Verify the file is the correct size */
if(file_size != empty_size)
TEST_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_fs_create() */
/*
* Test 1:
* Create free-space manager
* Add section A via H5FS_sect_add() with H5FS_ADD_RETURNED_SPACE
* Close the free-space manager
* Result: section A is serialized to the file
*
* Test 2:
* Create free-space manager with H5FS_CLS_GHOST_OBJ section class setting
* Add section A via H5FS_sect_add() with H5FS_ADD_RETURNED_SPACE
* Close the free-space manager
* Result: section A is not serialized to the file
*
* Test 3:
* Add section A via H5FS_sect_add() to allow shrinking with H5FS_ADD_RETURNED_SPACE
* Set EOF to be the ending address of section A
* Result: H5FS_sect_add() will shrink section A
*
* Test 4:
* Add section A via H5FS_sect_add() to allow shrinking with H5FS_ADD_DESERIALIZING
* Set EOF to be the ending address of section A
* Result: H5FS_sect_add() will not shrink section A
*
*/
static unsigned
test_fs_sect_add(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node = NULL;
unsigned init_flags=0;
h5_stat_size_t file_size=0, tmp_file_size=0, fr_meta_size=0;
unsigned can_shrink=FALSE;
TESTING("adding a section via H5FS_sect_add() to free-space: test 1");
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
/* Close file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if(NULL == (sect_node = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE20, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
fr_meta_size = H5FS_HEADER_SIZE(f) + H5FS_SINFO_PREFIX_SIZE(f);
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((tmp_file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_ERROR
if (tmp_file_size <= (file_size+fr_meta_size))
TEST_ERROR
PASSED();
TESTING("adding a section via H5FS_sect_add() to free-space with H5FS_CLS_GHOST_OBJ: test 2");
/* Get the size of a file w/empty heap*/
if((file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = H5FS_CLS_GHOST_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/* Create free list section node */
if(NULL == (sect_node = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE20, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node,
0, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node->sect_info.size;
state.tot_sect_count += 1;
state.ghost_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
fr_meta_size = H5FS_HEADER_SIZE(f);
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((tmp_file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_ERROR
if (tmp_file_size != (file_size+fr_meta_size))
TEST_ERROR
PASSED();
TESTING("adding a section via H5FS_sect_add() to free-space: test 3");
/* Create the file to work on */
if((file = H5Fcreate(filename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0)
FAIL_STACK_ERROR
/* Close file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
TEST_set_eoa((haddr_t)TEST_SECT_ADDR150); /* set end of file address for shrinking */
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = 0;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if(NULL == (sect_node = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
/*
* Add section A
*/
init_sect_node(sect_node, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
/* nothing in free-space */
HDmemset(&state, 0, sizeof(frspace_state_t));
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
TESTING("adding a section via H5FS_sect_add() to free-space: test 4");
/* Create the file to work on */
if((file = H5Fcreate(filename, H5F_ACC_TRUNC, H5P_DEFAULT, fapl)) < 0)
FAIL_STACK_ERROR
/* Close file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
/* Get the size of a file w/empty heap*/
if((file_size = h5_get_file_size(filename, fapl)) < 0)
TEST_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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
TEST_set_eoa((haddr_t)TEST_SECT_ADDR150); /* set end of file address for shrinking */
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = 0;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if(NULL == (sect_node = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
/*
* Add section A
*/
init_sect_node(sect_node, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node,
H5FS_ADD_DESERIALIZING, &can_shrink) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node) < 0)
TEST_ERROR
sect_node = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(sect_node)
TEST_sect_free((H5FS_section_info_t *)sect_node);
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_fs_sect_add() */
/*
* To verify the finding of a section with the requested-size from free-space
*
* Test 1: Free-space is empty and is not able to fulfill the requested-size
* Set up: free-space is started up but is empty
*
* Test 2: Add a section and find the section whose size is equal to the requested-size
* Set up: Add section A whose size is less than requested-size
* Add section B whose size is the same as requested-size with addr=b
* Add section C whose size is the same as requested-size with addr=c > b
* Add section D whose size is greater than requested-size
*
* Test 3: Add a section and find the section whose size is > requested-size
* Set up: Add section A whose size is less than requested-size
* Add section B whose size is greater than requested-size
*
* Test 4: Add a section but the section is not able to fulfill the requested-size
* Set up: Add section A whose size is less than requested-size
*
*/
static unsigned
test_fs_sect_find(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node1 = NULL, *sect_node2, *sect_node3 = NULL, *sect_node4 = NULL;
TEST_free_section_t *node;
htri_t node_found = FALSE;
unsigned init_flags=0;
TESTING("H5FS_sect_find(): free-space is empty");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
if(check_stats(f, frsp, &state))
TEST_ERROR
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE30, (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
PASSED();
TESTING("H5FS_sect_find() a section equal to requested-size from free-space");
/* reopen the free-space manager */
if(NULL == (frsp = H5FS_open(f, fs_addr, nclasses,
test_classes, NULL, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if (frsp->nclasses != nclasses)
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section C
*/
if(NULL == (sect_node3 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node3, (haddr_t)(TEST_SECT_ADDR200), (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node3,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node3->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section D
*/
if(NULL == (sect_node4 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node4, (haddr_t)TEST_SECT_ADDR300, (hsize_t)TEST_SECT_SIZE80, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node4,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node4->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE50, (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR100) || (node->sect_info.size != TEST_SECT_SIZE50))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* remove sections A, C and D */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node1) < 0)
FAIL_STACK_ERROR
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node3) < 0)
FAIL_STACK_ERROR
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node4) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node1) < 0)
TEST_ERROR
sect_node1 = NULL;
if(TEST_sect_free((H5FS_section_info_t *)sect_node3) < 0)
TEST_ERROR
sect_node3 = NULL;
if(TEST_sect_free((H5FS_section_info_t *)sect_node4) < 0)
TEST_ERROR
sect_node4 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
PASSED();
TESTING("H5FS_sect_find() a section greater than requested-size from free-space");
/* reopen the free-space manager */
if(NULL == (frsp = H5FS_open(f, fs_addr, nclasses,
test_classes, NULL, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if (frsp->nclasses != nclasses)
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR200, (hsize_t)TEST_SECT_SIZE80, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE50, (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found)
TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR200) || (node->sect_info.size < TEST_SECT_SIZE50))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
node = NULL;
/* remove sections A */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node1) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node1) < 0)
TEST_ERROR
sect_node1 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
PASSED();
TESTING("H5FS_sect_find(): cannot find a section with requested-size from free-space");
/* reopen the free-space manager */
if(NULL == (frsp = H5FS_open(f, fs_addr, nclasses,
test_classes, NULL, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
if (frsp->nclasses != nclasses)
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE50, (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
/* remove sections A */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node1) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node1) < 0)
TEST_ERROR
sect_node1 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(sect_node1)
TEST_sect_free((H5FS_section_info_t *)sect_node1);
if(sect_node3)
TEST_sect_free((H5FS_section_info_t *)sect_node3);
if(sect_node4)
TEST_sect_free((H5FS_section_info_t *)sect_node4);
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_fs_sect_find() */
/*
* To verify that sections are merged when adding sections to free-space
*
* Test 1:
* Set up:
* H5FS_CLS_SEPAR_OBJ (cls->flags) is not set
* H5FS_ADD_RETURNED_SPACE is passed to H5FS_sect_add()
*
* Add sections C, B, A & D that can be merged together
*
* Test 2:
* Set up:
* H5FS_CLS_SEPAR_OBJ (cls->flags) is set
* H5FS_ADD_RETURNED_SPACE is passed to H5FS_sect_add()
*
* Add sections A & B that can be merged together but cannot do so because H5FS_CLS_SEPAR_OBJ flag is set
*
* Test 3:
* Set up:
* H5FS_CLS_SEPAR_OBJ (cls->flags) is not set
* H5FS_ADD_RETURNED_SPACE is passed to H5FS_sect_add()
*
* Add 4 sections that adjoin each other as follows:
* section A is of section class type A
* section B is of section class type B
* section C is of section class type B
* section D is of section class type A
* Sections B & C are merged together but not section A nor D because:
* sections B & C are merged because of the same section class type
* section A cannot be merged with the merged section of B & C because of different section class type
* section D cannot be merged with the merged section of B & C because of different section class type
*/
static unsigned
test_fs_sect_merge(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node1=NULL, *sect_node2=NULL, *sect_node3=NULL, *sect_node4=NULL;
unsigned init_flags=0;
htri_t node_found = FALSE;
TEST_free_section_t *node;
TESTING("the merge of sections when H5FS_sect_add() to free-space: test 1");
/*
* TEST 1
*/
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section C
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += TEST_SECT_SIZE50;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* section B & C are merged */
state.tot_space += TEST_SECT_SIZE30;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node3 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node3, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE10, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node3,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* section A is merged with the merged section of B & C */
state.tot_space += TEST_SECT_SIZE10;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section D
*/
if(NULL == (sect_node4 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node4, (haddr_t)TEST_SECT_ADDR150, (hsize_t)TEST_SECT_SIZE80, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node4,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* section D is merged with the merged section of A & B & C */
state.tot_space += TEST_SECT_SIZE80;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* should be able to find the merged section of A, B, C & D */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE10+TEST_SECT_SIZE30+TEST_SECT_SIZE50+TEST_SECT_SIZE80), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR60) ||
(node->sect_info.size != (TEST_SECT_SIZE10+TEST_SECT_SIZE30+TEST_SECT_SIZE50+TEST_SECT_SIZE80)))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
/*
* TEST 2
*/
TESTING("the merge of sections when H5FS_sect_add() to free-space: test 2");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = H5FS_CLS_SEPAR_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += TEST_SECT_SIZE30;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* section A & B are not merged because H5FS_CLS_SEPAR_OBJ is set */
state.tot_space += TEST_SECT_SIZE50;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* should not be able to find the merged section of A & B */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE30+TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
/* remove section A from free-space */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node1) < 0)
FAIL_STACK_ERROR
/* remove section B from free-space */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node2) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node1) < 0)
TEST_ERROR
sect_node1 = NULL;
if(TEST_sect_free((H5FS_section_info_t *)sect_node2) < 0)
TEST_ERROR
sect_node2 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
/*
* TEST 3
*/
TESTING("the merge of sections when H5FS_sect_add() to free-space: test 3");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = 0; /* reset */
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE10, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += TEST_SECT_SIZE10;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE_NEW, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* sections A & B are not merged because H5FS_CLS_MERGE_SYM is set & section class type is different */
state.tot_space += TEST_SECT_SIZE30;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section C
*/
if(NULL == (sect_node3 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node3, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE_NEW, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node3,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* sections B & C are merged because H5FS_CLS_MERGE_SYM is set & section class type is the same */
state.tot_space += TEST_SECT_SIZE50;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section D
*/
if(NULL == (sect_node4 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node4, (haddr_t)TEST_SECT_ADDR150, (hsize_t)TEST_SECT_SIZE80, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node4,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/*
* section D is not merged with the merged section of B & C because
* H5FS_CLS_MERGE_SYM is set and section class type is different
*/
state.tot_space += TEST_SECT_SIZE80;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* should not be able to find a merged section of A, B, C & D */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE10+TEST_SECT_SIZE30+TEST_SECT_SIZE50+TEST_SECT_SIZE80), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
/* should be able to find the merged section of B & C */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE30+TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR70) ||
(node->sect_info.size != (TEST_SECT_SIZE30+TEST_SECT_SIZE50)))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* should be able to find section A */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE10), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR60) || (node->sect_info.size != TEST_SECT_SIZE10))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* should be able to find section D */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE80), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR150) || (node->sect_info.size != TEST_SECT_SIZE80))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(sect_node1)
TEST_sect_free((H5FS_section_info_t *)sect_node1);
if(sect_node2)
TEST_sect_free((H5FS_section_info_t *)sect_node2);
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_fs_sect_merge() */
/*
* To verify that sections are shrunk when adding sections to free-space
*
* Test 1:
* Set EOF to be the ending address of section A
* H5FS_CLS_SEPAR_OBJ (cls->flags) is not set when creating free-space manager
* Add section A to allow shrinking but is not shrunk because its section class type
* TEST_FSPACE_SECT_TYPE_NEW does not define "can_shrink"
* Result:section A is not shrunk and section A is still in free-space
*
* Re-add section A to allow shrinking and with section class type TEST_FSPACE_SECT_TYPE
* that defines "can_shrink"
* Result:section A is shrunk and there is nothing in free-space
*
* Test 2:
* Set EOF to be greater than the ending address of section A
* Set H5FS_CLS_SEPAR_OBJ (cls->flags) when creating free-space manager
*
* Add section A to allow shrinking but is not shrunk because it is not at EOF,
* and section A is not on the merge list due to H5FS_CLS_SEPAR_OBJ
* Add section B to allow shrinking and whose ending address is the same as eof.
* Section B is not merged with section A because of H5FS_CLS_SEPAR_OBJ but it is shrunk
* Result: section A is still in free-space
*
* Test 3:
* Set EOF to be greater than the ending address of section A
* H5FS_CLS_SEPAR_OBJ (cls->flags) is not set when creating free-space manager
*
* Add section A to allow shrinking but is not shrunk because it is not at EOF,
* and section A is on the merge list
* Add section B to allow shrinking and whose ending address is the same as eof.
* Section B is merged with section A and then shrunk.
* Result: free-space should be empty
*/
static unsigned
test_fs_sect_shrink(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node1=NULL, *sect_node2=NULL;
unsigned init_flags=0;
unsigned can_shrink=FALSE;
htri_t node_found = FALSE;
TEST_free_section_t *node;
TESTING("shrinking of sections when H5FS_sect_add() to free-space: test 1");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
TEST_set_eoa((haddr_t)TEST_SECT_ADDR150); /* set end of file address for shrinking */
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A that allow shrinking but its section class type does not define "can_shrink"
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE_NEW, H5FS_SECT_LIVE);
can_shrink = FALSE;
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* section A should still be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR100) || (node->sect_info.size != TEST_SECT_SIZE50))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/*
* Re-add section A that allow shrinking and its section class type defines "can_shrink"
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
can_shrink = FALSE;
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
/* should have nothing in free-space */
HDmemset(&state, 0, sizeof(frspace_state_t));
if(check_stats(f, frsp, &state))
TEST_ERROR
/* section A should not be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
TESTING("shrinking of sections when H5FS_sect_add() to free-space: test 2");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
TEST_set_eoa((haddr_t)TEST_SECT_ADDR150); /* set end of file address for shrinking */
/* does not allow merging */
init_flags = H5FS_CLS_SEPAR_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE20, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
/* free-space should be the same since section B is shrunk */
if(check_stats(f, frsp, &state))
TEST_ERROR
/* section B should not be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found)
TEST_ERROR
if(check_stats(f, frsp, &state))
TEST_ERROR
/* section A should still be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE20), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (!node_found) TEST_ERROR
if ((node->sect_info.addr != TEST_SECT_ADDR80) || (node->sect_info.size != TEST_SECT_SIZE20))
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
TESTING("shrinking of sections when H5FS_sect_add() to free-space: test 3");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
TEST_set_eoa((haddr_t)TEST_SECT_ADDR150); /* set end of file address for shrinking */
init_flags = 0; /* reset */
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, &can_shrink) < 0)
FAIL_STACK_ERROR
/* section A & B are merged and then strunk, so there is nothing in free-space */
HDmemset(&state, 0, sizeof(frspace_state_t));
if(check_stats(f, frsp, &state))
TEST_ERROR
/* section B should not be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE50), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found)
TEST_ERROR
/* section A should not be there in free-space */
if((node_found = H5FS_sect_find(f, frsp,
(hsize_t)(TEST_SECT_SIZE30), (H5FS_section_info_t **)&node)) < 0)
FAIL_STACK_ERROR
if (node_found) TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_sect_shrink() */
/*
* To verify a section's class is changed via H5FS_sect_change_class()
*
* Test 1:
* Add section A with TEST_FSPACE_SECT_TYPE class type with H5FS_CLS_GHOST_OBJ setting
* Add section B with TEST_FSPACE_SECT_TYPE_NONE class type without H5FS_CLS_GHOST_OBJ setting
* Change section A's class to the second section's class
* Result: serial_sect_count is incremented by 1; ghost_sect_count is decremented by 1
*
* Test 2:
* Add section A with TEST_FSPACE_SECT_TYPE class type with H5FS_CLS_SEPAR_OBJ setting
* Add section B with TEST_FSPACE_SECT_TYPE_NONE class type without H5FS_CLS_SEPAR_OBJ setting
* Add section C with TEST_FSPACE_SECT_TYPE_NONE class type without H5FS_CLS_SEPAR_OBJ setting
* Sections B & C are on the merge list
* Change section class of B and C to A's section class
* Result: the merge list should be null and the class of sections B & C should be changed
*/
static unsigned
test_fs_sect_change_class(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node1=NULL, *sect_node2=NULL, *sect_node3=NULL;
unsigned init_flags=0;
TEST_free_section_t *node;
TESTING("the change of section class via H5FS_sect_change_class() in free-space: Test 1");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
init_flags = H5FS_CLS_GHOST_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR60, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += TEST_SECT_SIZE30;
state.tot_sect_count += 1;
state.ghost_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE_NONE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += TEST_SECT_SIZE50;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if (H5FS_sect_change_class(f, frsp, (H5FS_section_info_t *)sect_node1,
TEST_FSPACE_SECT_TYPE_NONE) < 0)
TEST_ERROR
state.serial_sect_count += 1;
state.ghost_sect_count -=1;
if(check_stats(f, frsp, &state))
TEST_ERROR
if(H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE30, (H5FS_section_info_t **)&node) < 0)
FAIL_STACK_ERROR
if (node->sect_info.type != TEST_FSPACE_SECT_TYPE_NONE)
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node2) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node2) < 0)
TEST_ERROR
sect_node2 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
/*
* TEST 2
*/
TESTING("the merge of sections when H5FS_sect_add() to free-space: test 2");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
init_flags = H5FS_CLS_SEPAR_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE30, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE50, TEST_FSPACE_SECT_TYPE_NONE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/*
* Add section C
*/
if(NULL == (sect_node3 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node3, (haddr_t)TEST_SECT_ADDR200, (hsize_t)TEST_SECT_SIZE80, TEST_FSPACE_SECT_TYPE_NONE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node3,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
/* change the class of B to A's class */
if (H5FS_sect_change_class(f, frsp, (H5FS_section_info_t *)sect_node2,
TEST_FSPACE_SECT_TYPE) < 0)
TEST_ERROR
/* change the class of C to A's class */
if (H5FS_sect_change_class(f, frsp, (H5FS_section_info_t *)sect_node3,
TEST_FSPACE_SECT_TYPE) < 0)
TEST_ERROR
/* the merge_list should be empty */
if (frsp->sinfo->merge_list)
if (H5SL_count(frsp->sinfo->merge_list))
TEST_ERROR
/* verify that section B has changed class */
if(H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE50, (H5FS_section_info_t **)&node) < 0)
FAIL_STACK_ERROR
if (node->sect_info.type != TEST_FSPACE_SECT_TYPE)
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* verify that section C has changed class */
if(H5FS_sect_find(f, frsp,
(hsize_t)TEST_SECT_SIZE80, (H5FS_section_info_t **)&node) < 0)
FAIL_STACK_ERROR
if (node->sect_info.type != TEST_FSPACE_SECT_TYPE)
TEST_ERROR
if(TEST_sect_free((H5FS_section_info_t *)node) < 0)
TEST_ERROR
/* remove section A from free-space */
if(H5FS_sect_remove(f, frsp, (H5FS_section_info_t *)sect_node1) < 0)
FAIL_STACK_ERROR
/* Free the section node(s) */
if(TEST_sect_free((H5FS_section_info_t *)sect_node1) < 0)
TEST_ERROR
sect_node1 = NULL;
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(sect_node1)
TEST_sect_free((H5FS_section_info_t *)sect_node1);
if(sect_node2)
TEST_sect_free((H5FS_section_info_t *)sect_node2);
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_sect_change_class() */
/*
* To verify the extension of a block using space from a section in free-space
*
* Test 1: Try to extend the block by requested-size, which is equal to section B's size
* Add section A (addr=70, size=5)
* Add section B (addr=100, size=40)
* Try to extend the block (addr=80, size=20) by 40, which is the same as section B's size
* Result: succeed in extending the block
*
* Test 2: Try to extend the block by requested-size, which is greater than section B's size
* Add section A (addr=70, size=5)
* Add section B (addr=100, size=40)
* Try to extend the block (addr=80, size=20) by 50, which is greater than section B's size
* Result: fail in extending the block
*
* Test 3: Try to extend the block by requested-size, which is less than section B's size
* Add section A (addr=70, size=5)
* Add section B (addr=100, size=40)
* Try to extend the block (addr=80, size=20) by 30, which is less than section B's size
* Result: succeed in extending the block and a section of size=10 is left in free-space
*
* Test 4: Try to extend the block which does not adjoin section B
* Add section A (addr=70, size=5)
* Add section B (addr=100, size=40)
* Try to extend the block (addr=80, size=15) by 40
* Result: fail in extending the block because:
* the block does not adjoin section B (80+15 != addr of section B (80))
* even though the requested-size is equal to section B's size
*
*/
static unsigned
test_fs_sect_extend(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
frspace_state_t state; /* State of free space*/
TEST_free_section_t *sect_node1=NULL, *sect_node2=NULL;
unsigned init_flags=0;
htri_t status; /* Status of 'try' calls */
TESTING("a block's extension by requested-size which is = adjoining free section's size: Test 1");
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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
/*
* TEST 1
*/
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE5, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE40, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Extend a block by requested-size */
if((status = H5FS_sect_try_extend(f, frsp, (haddr_t)TEST_SECT_SIZE80, (hsize_t)TEST_SECT_SIZE20, (hsize_t)TEST_SECT_SIZE40, 0, NULL)) < 0)
FAIL_STACK_ERROR
if(FALSE == status)
TEST_ERROR
/* Succeed in extending the block: free space info is decremented accordingly */
state.tot_space -= (hsize_t)TEST_SECT_SIZE40;
state.tot_sect_count -= 1;
state.serial_sect_count -= 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
PASSED();
/*
* TEST 2
*/
TESTING("a block's extension by requested-size which is > adjoining free section's size: Test 2");
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE5, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE40, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Extend the block by requested-size */
if((status = H5FS_sect_try_extend(f, frsp, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE20, (hsize_t)TEST_SECT_SIZE50, 0, NULL)) < 0)
FAIL_STACK_ERROR
if(TRUE == status)
TEST_ERROR
/* Not able to extend the block: free space info remains the same */
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
PASSED();
/*
* Test 3
*/
TESTING("a block's extension by requested-size which is < adjoining free section's size: Test 3");
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE5, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE40, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Extend the block by requested-size */
if((status = H5FS_sect_try_extend(f, frsp, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE20, (hsize_t)TEST_SECT_SIZE30, 0, NULL)) < 0)
TEST_ERROR
if(FALSE == status)
TEST_ERROR
/* Succeed in extending the block: total free space is decreased but other info remains the same */
state.tot_space -= 30;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
PASSED();
/*
* TEST 4
*/
TESTING("a block's extension by requested-size which does not adjoin any free section: Test 4");
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
/*
* Add section A
*/
if(NULL == (sect_node1 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node1, (haddr_t)TEST_SECT_ADDR70, (hsize_t)TEST_SECT_SIZE5, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node1,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
HDmemset(&state, 0, sizeof(frspace_state_t));
state.tot_space += sect_node1->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/*
* Add section B
*/
if(NULL == (sect_node2 = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
init_sect_node(sect_node2, (haddr_t)TEST_SECT_ADDR100, (hsize_t)TEST_SECT_SIZE40, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node2,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
state.tot_space += sect_node2->sect_info.size;
state.tot_sect_count += 1;
state.serial_sect_count += 1;
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Extend the block by requested-size */
if((status = H5FS_sect_try_extend(f, frsp, (haddr_t)TEST_SECT_ADDR80, (hsize_t)TEST_SECT_SIZE15, (hsize_t)TEST_SECT_SIZE40, 0, NULL)) < 0)
TEST_ERROR
if(TRUE == status)
TEST_ERROR
/* Not able to extend the block: free space manager info remains the same */
if(check_stats(f, frsp, &state))
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
PASSED();
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
return 0;
error:
H5E_BEGIN_TRY {
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_sect_extend() */
/*
* To verify the iteration of free-space sections
*
* Create free-space manager with H5FS_CLS_SEPAR_OBJ
* Create a whole bunch of sections
* Iterate through all sections and collect size and count for all sections
* Check info with H5FS_sect_stat()
*/
static unsigned
test_fs_sect_iterate(hid_t fapl)
{
hid_t file = -1; /* File ID */
char filename[FILENAME_LEN]; /* Filename to use */
H5F_t *f = NULL; /* Internal file object pointer */
H5FS_t *frsp = NULL; /* pointer to free space structure */
haddr_t fs_addr=HADDR_UNDEF; /* address of free space */
uint16_t nclasses;
H5FS_create_t cparam; /* creation parameters */
TEST_free_section_t *sect_node=NULL;
unsigned init_flags=0, sect_size;
TEST_iter_ud_t udata;
int i;
hsize_t tot_space, nsects;
TESTING("iteration of sections in the free-space manager");
/* 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 = (H5F_t *)H5VL_object(file)))
FAIL_STACK_ERROR
init_cparam(&cparam);
nclasses = NELMTS(test_classes);
udata.tot_size = 0;
udata.tot_sect_count = 0;
/* Tag with the global free space tag */
H5AC_tag(H5AC__FREESPACE_TAG, NULL);
init_flags = H5FS_CLS_SEPAR_OBJ;
if(NULL == (frsp = H5FS_create(f, &fs_addr,
&cparam, nclasses, test_classes, &init_flags, (hsize_t)FSPACE_THRHD_DEF, (hsize_t)FSPACE_ALIGN_DEF)))
FAIL_STACK_ERROR
if(!H5F_addr_defined(fs_addr))
TEST_ERROR
for (i = 1; i <= NUM_SECTIONS; i++) {
if(NULL == (sect_node = (TEST_free_section_t *)HDmalloc(sizeof(TEST_free_section_t))))
FAIL_STACK_ERROR
sect_size = (unsigned)((i-1) % 9) + 1;
init_sect_node(sect_node, (haddr_t)i*10, (hsize_t)sect_size, TEST_FSPACE_SECT_TYPE, H5FS_SECT_LIVE);
if(H5FS_sect_add(f, frsp, (H5FS_section_info_t *)sect_node,
H5FS_ADD_RETURNED_SPACE, NULL) < 0)
FAIL_STACK_ERROR
} /* end for */
if(H5FS_sect_iterate(f, frsp, TEST_sects_cb, &udata) < 0)
TEST_ERROR
H5FS_sect_stats(frsp, &tot_space, &nsects);
if (udata.tot_size != tot_space)
TEST_ERROR
if (udata.tot_sect_count != nsects)
TEST_ERROR
/* Close the free space manager */
if(H5FS_close(f, frsp) < 0)
FAIL_STACK_ERROR
frsp = NULL;
/* Delete free space manager */
if(H5FS_delete(f, fs_addr) < 0)
FAIL_STACK_ERROR
fs_addr = HADDR_UNDEF;
/* Close the file */
if(H5Fclose(file) < 0)
FAIL_STACK_ERROR
PASSED();
return 0;
error:
H5E_BEGIN_TRY {
if(frsp)
H5FS_close(f, frsp);
H5Fclose(file);
} H5E_END_TRY;
return 1;
} /* test_fs_sect_iterate() */
int
main(void)
{
hid_t fapl = -1; /* File access property list for data files */
unsigned nerrors = 0; /* Cumulative error count */
hbool_t api_ctx_pushed = FALSE; /* Whether API context pushed */
h5_reset();
if((fapl = h5_fileaccess()) < 0) {
nerrors++;
PUTS_ERROR("Can't get VFD-dependent fapl")
} /* end if */
/* Push API context */
if(H5CX_push() < 0) FAIL_STACK_ERROR
api_ctx_pushed = TRUE;
/* make sure alignment is not set for tests to succeed */
if(H5Pset_alignment(fapl, (hsize_t)1, (hsize_t)1) < 0) {
nerrors++;
PUTS_ERROR("Can't set alignment")
} /* end if */
nerrors += test_fs_create(fapl);
nerrors += test_fs_sect_add(fapl);
nerrors += test_fs_sect_merge(fapl);
nerrors += test_fs_sect_shrink(fapl);
nerrors += test_fs_sect_find(fapl);
nerrors += test_fs_sect_change_class(fapl);
nerrors += test_fs_sect_extend(fapl);
nerrors += test_fs_sect_iterate(fapl);
/* Verify symbol table messages are cached */
nerrors += (h5_verify_cached_stabs(FILENAME, fapl) < 0 ? 1 : 0);
if(nerrors)
goto error;
HDputs("All free-space tests passed.");
/* Pop API context */
if(api_ctx_pushed && H5CX_pop() < 0) FAIL_STACK_ERROR
api_ctx_pushed = FALSE;
h5_cleanup(FILENAME, fapl);
HDexit(EXIT_SUCCESS);
error:
HDputs("*** TESTS FAILED ***");
H5E_BEGIN_TRY {
H5Pclose(fapl);
} H5E_END_TRY;
if(api_ctx_pushed) H5CX_pop();
HDexit(EXIT_FAILURE);
} /* main() */