8291970: Add TableStatistics get function to ResourceHashtable
Reviewed-by: iklam, ccheung
This commit is contained in:
parent
cbc9040f3a
commit
f5b3618c42
@ -26,6 +26,8 @@
|
||||
#define SHARE_UTILITIES_RESOURCEHASH_HPP
|
||||
|
||||
#include "memory/allocation.hpp"
|
||||
#include "utilities/numberSeq.hpp"
|
||||
#include "utilities/tableStatistics.hpp"
|
||||
|
||||
template<typename K, typename V>
|
||||
class ResourceHashtableNode : public ResourceObj {
|
||||
@ -259,6 +261,26 @@ class ResourceHashtableBase : public STORAGE {
|
||||
}
|
||||
}
|
||||
|
||||
template<typename Function>
|
||||
TableStatistics statistics_calculate(Function size_function) const {
|
||||
NumberSeq summary;
|
||||
size_t literal_bytes = 0;
|
||||
Node* const* bucket = table();
|
||||
const unsigned sz = table_size();
|
||||
while (bucket < bucket_at(sz)) {
|
||||
Node* node = *bucket;
|
||||
int count = 0;
|
||||
while (node != NULL) {
|
||||
literal_bytes += size_function(node->_key, node->_value);
|
||||
count++;
|
||||
node = node->_next;
|
||||
}
|
||||
summary.add((double)count);
|
||||
++bucket;
|
||||
}
|
||||
return TableStatistics(summary, literal_bytes, sizeof(Node*), sizeof(Node));
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
template<unsigned TABLE_SIZE, typename K, typename V>
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2019, 2022, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -91,7 +91,7 @@ TableStatistics::TableStatistics() :
|
||||
_add_rate(0), _remove_rate(0) {
|
||||
}
|
||||
|
||||
TableStatistics::TableStatistics(TableRateStatistics& rate_stats, NumberSeq summary, size_t literal_bytes, size_t bucket_bytes, size_t node_bytes) :
|
||||
TableStatistics::TableStatistics(NumberSeq summary, size_t literal_bytes, size_t bucket_bytes, size_t node_bytes) :
|
||||
_literal_bytes(literal_bytes),
|
||||
_number_of_buckets(0), _number_of_entries(0),
|
||||
_maximum_bucket_size(0), _average_bucket_size(0),
|
||||
@ -114,7 +114,12 @@ TableStatistics::TableStatistics(TableRateStatistics& rate_stats, NumberSeq summ
|
||||
|
||||
_bucket_size = (_number_of_buckets <= 0) ? 0 : (_bucket_bytes / _number_of_buckets);
|
||||
_entry_size = (_number_of_entries <= 0) ? 0 : (_entry_bytes / _number_of_entries);
|
||||
}
|
||||
|
||||
TableStatistics::TableStatistics(TableRateStatistics& rate_stats,
|
||||
NumberSeq summary, size_t literal_bytes,
|
||||
size_t bucket_bytes, size_t node_bytes) :
|
||||
TableStatistics(summary, literal_bytes, bucket_bytes, node_bytes) {
|
||||
#if INCLUDE_JFR
|
||||
if (Jfr::is_recording()) {
|
||||
rate_stats.stamp();
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2019, 2022, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -82,6 +82,7 @@ public:
|
||||
float _remove_rate;
|
||||
|
||||
TableStatistics();
|
||||
TableStatistics(NumberSeq summary, size_t literal_bytes, size_t bucket_bytes, size_t node_bytes);
|
||||
TableStatistics(TableRateStatistics& rate_stats, NumberSeq summary, size_t literal_bytes, size_t bucket_bytes, size_t node_bytes);
|
||||
~TableStatistics();
|
||||
|
||||
|
@ -446,3 +446,46 @@ TEST_VM_F(ResourceHashtableDeleteTest, check_delete_ptr) {
|
||||
// Removal should make the refcount be the original refcount.
|
||||
ASSERT_EQ(s->refcount(), s_orig_count) << "refcount should be as we started";
|
||||
}
|
||||
|
||||
class ResourceHashtablePrintTest : public ::testing::Test {
|
||||
public:
|
||||
class TestValue {
|
||||
int _i;
|
||||
int _j;
|
||||
int _k;
|
||||
public:
|
||||
TestValue(int i) : _i(i), _j(i+1), _k(i+2) {}
|
||||
};
|
||||
ResourceHashtable<int, TestValue*, 30, ResourceObj::C_HEAP, mtTest> _test_table;
|
||||
|
||||
class TableDeleter {
|
||||
public:
|
||||
bool do_entry(int& key, TestValue*& val) {
|
||||
delete val;
|
||||
return true;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
TEST_VM_F(ResourceHashtablePrintTest, print_test) {
|
||||
for (int i = 0; i < 300; i++) {
|
||||
TestValue* tv = new TestValue(i);
|
||||
_test_table.put(i, tv); // all the entries can be the same.
|
||||
}
|
||||
auto printer = [&] (int& key, TestValue*& val) {
|
||||
return sizeof(*val);
|
||||
};
|
||||
TableStatistics ts = _test_table.statistics_calculate(printer);
|
||||
ResourceMark rm;
|
||||
stringStream st;
|
||||
ts.print(&st, "TestTable");
|
||||
// Verify output in string
|
||||
const char* strings[] = {
|
||||
"Number of buckets", "Number of entries", "300", "Number of literals", "Average bucket size", "Maximum bucket size" };
|
||||
for (const auto& str : strings) {
|
||||
ASSERT_TRUE(strstr(st.as_string(), str) != nullptr) << "string not present " << str;
|
||||
}
|
||||
// Cleanup: need to delete pointers in entries
|
||||
TableDeleter deleter;
|
||||
_test_table.unlink(&deleter);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user