From f0b94cb4eb94c5e0a21b1e2acc6a2055759e887b Mon Sep 17 00:00:00 2001 From: shade Date: Fri, 18 Jan 2019 17:05:41 +0100 Subject: [PATCH] 8217315: Proper units should print more significant digits Reviewed-by: stuefe, tschatzl --- src/share/vm/prims/jni.cpp | 1 + src/share/vm/utilities/globalDefinitions.cpp | 63 ++++++++++++++++++++ src/share/vm/utilities/globalDefinitions.hpp | 18 ++++-- 3 files changed, 76 insertions(+), 6 deletions(-) diff --git a/src/share/vm/prims/jni.cpp b/src/share/vm/prims/jni.cpp index 51b453ee5..9947a2634 100644 --- a/src/share/vm/prims/jni.cpp +++ b/src/share/vm/prims/jni.cpp @@ -5121,6 +5121,7 @@ void execute_internal_vm_tests() { run_unit_test(TestMetachunk_test()); run_unit_test(TestVirtualSpaceNode_test()); run_unit_test(GlobalDefinitions::test_globals()); + run_unit_test(GlobalDefinitions::test_proper_unit()); run_unit_test(GCTimerAllTest::all()); run_unit_test(arrayOopDesc::test_max_array_length()); run_unit_test(CollectedHeap::test_is_in()); diff --git a/src/share/vm/utilities/globalDefinitions.cpp b/src/share/vm/utilities/globalDefinitions.cpp index 20c11862e..888e8d453 100644 --- a/src/share/vm/utilities/globalDefinitions.cpp +++ b/src/share/vm/utilities/globalDefinitions.cpp @@ -384,4 +384,67 @@ void GlobalDefinitions::test_globals() { } } +#define EXPECT_EQ(expected, actual) \ + assert(expected == actual, "Test failed"); +#define EXPECT_STREQ(expected, actual) \ + assert(strcmp(expected, actual) == 0, "Test failed"); + +void GlobalDefinitions::test_proper_unit() { + EXPECT_EQ(0u, byte_size_in_proper_unit(0u)); + EXPECT_STREQ("B", proper_unit_for_byte_size(0u)); + + EXPECT_EQ(1u, byte_size_in_proper_unit(1u)); + EXPECT_STREQ("B", proper_unit_for_byte_size(1u)); + + EXPECT_EQ(1023u, byte_size_in_proper_unit(K - 1)); + EXPECT_STREQ("B", proper_unit_for_byte_size(K - 1)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(K)); + EXPECT_STREQ("B", proper_unit_for_byte_size(K)); + + EXPECT_EQ(1025u, byte_size_in_proper_unit(K + 1)); + EXPECT_STREQ("B", proper_unit_for_byte_size(K + 1)); + + EXPECT_EQ(51200u, byte_size_in_proper_unit(50*K)); + EXPECT_STREQ("B", proper_unit_for_byte_size(50*K)); + + EXPECT_EQ(1023u, byte_size_in_proper_unit(M - 1)); + EXPECT_STREQ("K", proper_unit_for_byte_size(M - 1)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(M)); + EXPECT_STREQ("K", proper_unit_for_byte_size(M)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(M + 1)); + EXPECT_STREQ("K", proper_unit_for_byte_size(M + 1)); + + EXPECT_EQ(1025u, byte_size_in_proper_unit(M + K)); + EXPECT_STREQ("K", proper_unit_for_byte_size(M + K)); + + EXPECT_EQ(51200u, byte_size_in_proper_unit(50*M)); + EXPECT_STREQ("K", proper_unit_for_byte_size(50*M)); + +#ifdef _LP64 + EXPECT_EQ(1023u, byte_size_in_proper_unit(G - 1)); + EXPECT_STREQ("M", proper_unit_for_byte_size(G - 1)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(G)); + EXPECT_STREQ("M", proper_unit_for_byte_size(G)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(G + 1)); + EXPECT_STREQ("M", proper_unit_for_byte_size(G + 1)); + + EXPECT_EQ(1024u, byte_size_in_proper_unit(G + K)); + EXPECT_STREQ("M", proper_unit_for_byte_size(G + K)); + + EXPECT_EQ(1025u, byte_size_in_proper_unit(G + M)); + EXPECT_STREQ("M", proper_unit_for_byte_size(G + M)); + + EXPECT_EQ(51200u, byte_size_in_proper_unit(50*G)); + EXPECT_STREQ("M", proper_unit_for_byte_size(50*G)); +#endif +} + +#undef EXPECT_EQ +#undef EXPECT_STREQ + #endif // PRODUCT diff --git a/src/share/vm/utilities/globalDefinitions.hpp b/src/share/vm/utilities/globalDefinitions.hpp index 6824e3cc4..075352adc 100644 --- a/src/share/vm/utilities/globalDefinitions.hpp +++ b/src/share/vm/utilities/globalDefinitions.hpp @@ -211,15 +211,20 @@ const int NANOUNITS = 1000000000; // nano units per base unit const jlong NANOSECS_PER_SEC = CONST64(1000000000); const jint NANOSECS_PER_MILLISEC = 1000000; +// Proper units routines try to maintain at least three significant digits. +// In worst case, it would print five significant digits with lower prefix. +// G is close to MAX_SIZE on 32-bit platforms, so its product can easily overflow, +// and therefore we need to be careful. + inline const char* proper_unit_for_byte_size(size_t s) { #ifdef _LP64 - if (s >= 10*G) { + if (s >= 100*G) { return "G"; } #endif - if (s >= 10*M) { + if (s >= 100*M) { return "M"; - } else if (s >= 10*K) { + } else if (s >= 100*K) { return "K"; } else { return "B"; @@ -229,13 +234,13 @@ inline const char* proper_unit_for_byte_size(size_t s) { template inline T byte_size_in_proper_unit(T s) { #ifdef _LP64 - if (s >= 10*G) { + if (s >= 100*G) { return (T)(s/G); } #endif - if (s >= 10*M) { + if (s >= 100*M) { return (T)(s/M); - } else if (s >= 10*K) { + } else if (s >= 100*K) { return (T)(s/K); } else { return s; @@ -1486,6 +1491,7 @@ static inline void* dereference_vptr(const void* addr) { class GlobalDefinitions { public: static void test_globals(); + static void test_proper_unit(); }; #endif // PRODUCT -- GitLab