< prev index next > test/hotspot/gtest/metaspace/test_blocktree.cpp
Print this page
*/
#include "precompiled.hpp"
#include "memory/metaspace/blockTree.hpp"
#include "memory/metaspace/counters.hpp"
#include "memory/resourceArea.hpp"
// #define LOG_PLEASE
#include "metaspaceGtestCommon.hpp"
using metaspace::BlockTree;
using metaspace::MemRangeCounter;
// Small helper. Given a 0-terminated array of sizes, a feeder buffer and a tree,
// add blocks of these sizes to the tree in the order they appear in the array.
! static void create_nodes(const size_t sizes[], FeederBuffer& fb, BlockTree& bt) {
for (int i = 0; sizes[i] > 0; i ++) {
size_t s = sizes[i];
MetaWord* p = fb.get(s);
bt.add_block(p, s);
}
*/
#include "precompiled.hpp"
#include "memory/metaspace/blockTree.hpp"
#include "memory/metaspace/counters.hpp"
+ #include "memory/metaspace/metablock.hpp"
#include "memory/resourceArea.hpp"
// #define LOG_PLEASE
#include "metaspaceGtestCommon.hpp"
using metaspace::BlockTree;
using metaspace::MemRangeCounter;
+ using metaspace::MetaBlock;
+
+ struct TestedBlockTree : public BlockTree {
+ void add_block(MetaWord* p, size_t word_size) {
+ BlockTree::add_block(MetaBlock(p, word_size));
+ }
+ MetaWord* remove_block(size_t requested_size, size_t* real_size) {
+ MetaBlock result = BlockTree::remove_block(requested_size);
+ (*real_size) = result.word_size();
+ return result.base();
+ }
+ };
// Small helper. Given a 0-terminated array of sizes, a feeder buffer and a tree,
// add blocks of these sizes to the tree in the order they appear in the array.
! static void create_nodes(const size_t sizes[], FeederBuffer& fb, TestedBlockTree& bt) {
for (int i = 0; sizes[i] > 0; i ++) {
size_t s = sizes[i];
MetaWord* p = fb.get(s);
bt.add_block(p, s);
}
} \
}
TEST_VM(metaspace, BlockTree_basic) {
! BlockTree bt;
CHECK_BT_CONTENT(bt, 0, 0);
size_t real_size = 0;
MetaWord* p = nullptr;
MetaWord arr[10000];
} \
}
TEST_VM(metaspace, BlockTree_basic) {
! TestedBlockTree bt;
CHECK_BT_CONTENT(bt, 0, 0);
size_t real_size = 0;
MetaWord* p = nullptr;
MetaWord arr[10000];
// Given a sequence of (0-terminated) sizes, add blocks of those sizes to the tree in the order given. Then, ask
// for a request size and check that it is the expected result.
static void test_find_nearest_fit_with_tree(const size_t sizes[], size_t request_size) {
! BlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
DEBUG_ONLY(bt.verify();)
// Given a sequence of (0-terminated) sizes, add blocks of those sizes to the tree in the order given. Then, ask
// for a request size and check that it is the expected result.
static void test_find_nearest_fit_with_tree(const size_t sizes[], size_t request_size) {
! TestedBlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
DEBUG_ONLY(bt.verify();)
30, 17, 10, 28,
50, 32, 51, 35,
0 // stop
};
! BlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
for (int i = BlockTree::MinWordSize; i <= 60; i ++) {
30, 17, 10, 28,
50, 32, 51, 35,
0 // stop
};
! TestedBlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
for (int i = BlockTree::MinWordSize; i <= 60; i ++) {
// Test repeated adding and removing of blocks of the same size, which
// should exercise the list-part of the tree.
TEST_VM(metaspace, BlockTree_basic_siblings)
{
! BlockTree bt;
FeederBuffer fb(4 * K);
CHECK_BT_CONTENT(bt, 0, 0);
const size_t test_size = BlockTree::MinWordSize;
// Test repeated adding and removing of blocks of the same size, which
// should exercise the list-part of the tree.
TEST_VM(metaspace, BlockTree_basic_siblings)
{
! TestedBlockTree bt;
FeederBuffer fb(4 * K);
CHECK_BT_CONTENT(bt, 0, 0);
const size_t test_size = BlockTree::MinWordSize;
30, 17, 10, 28,
50, 32, 51, 35,
0 // stop
};
! BlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
ResourceMark rm;
30, 17, 10, 28,
50, 32, 51, 35,
0 // stop
};
! TestedBlockTree bt;
FeederBuffer fb(4 * K);
create_nodes(sizes, fb, bt);
ResourceMark rm;
// Test that an overwritten node would result in an assert and a printed tree
TEST_VM_ASSERT_MSG(metaspace, BlockTree_overwriter_test, ".*failed: Invalid node") {
static const size_t sizes1[] = { 30, 17, 0 };
static const size_t sizes2[] = { 12, 12, 0 };
! BlockTree bt;
FeederBuffer fb(4 * K);
// some nodes...
create_nodes(sizes1, fb, bt);
// Test that an overwritten node would result in an assert and a printed tree
TEST_VM_ASSERT_MSG(metaspace, BlockTree_overwriter_test, ".*failed: Invalid node") {
static const size_t sizes1[] = { 30, 17, 0 };
static const size_t sizes2[] = { 12, 12, 0 };
! TestedBlockTree bt;
FeederBuffer fb(4 * K);
// some nodes...
create_nodes(sizes1, fb, bt);
class BlockTreeTest {
FeederBuffer _fb;
! BlockTree _bt[2];
MemRangeCounter _cnt[2];
RandSizeGenerator _rgen;
#define CHECK_COUNTERS \
class BlockTreeTest {
FeederBuffer _fb;
! TestedBlockTree _bt[2];
MemRangeCounter _cnt[2];
RandSizeGenerator _rgen;
#define CHECK_COUNTERS \
// Drain the trees. While draining, observe the order of the drained items.
void drain_all() {
for (int which = 0; which < 2; which++) {
! BlockTree* bt = _bt + which;
size_t last_size = 0;
while (!bt->is_empty()) {
// We only query for the minimal size. Actually returned size should be
// monotonously growing since remove_block should always return the closest fit.
// Drain the trees. While draining, observe the order of the drained items.
void drain_all() {
for (int which = 0; which < 2; which++) {
! TestedBlockTree* bt = _bt + which;
size_t last_size = 0;
while (!bt->is_empty()) {
// We only query for the minimal size. Actually returned size should be
// monotonously growing since remove_block should always return the closest fit.
< prev index next >