2323 */
2424#include " precompiled.hpp"
2525#include " jvm.h"
26+ #include " logging/log.hpp"
27+ #include " logging/logStream.hpp"
2628#include " memory/metaspaceUtils.hpp"
2729#include " runtime/atomic.hpp"
30+ #include " runtime/globals.hpp"
2831#include " runtime/orderAccess.hpp"
2932#include " runtime/vmThread.hpp"
3033#include " runtime/vmOperations.hpp"
3134#include " services/memBaseline.hpp"
3235#include " services/memReporter.hpp"
3336#include " services/mallocTracker.inline.hpp"
3437#include " services/memTracker.hpp"
38+ #include " services/nmtCommon.hpp"
39+ #include " services/nmtPreInit.hpp"
3540#include " services/threadStackTracker.hpp"
3641#include " utilities/debug.hpp"
3742#include " utilities/defaultStream.hpp"
@@ -45,79 +50,44 @@ volatile NMT_TrackingLevel MemTracker::_tracking_level = NMT_unknown;
4550NMT_TrackingLevel MemTracker::_cmdline_tracking_level = NMT_unknown;
4651
4752MemBaseline MemTracker::_baseline;
48- bool MemTracker::_is_nmt_env_valid = true ;
4953
50- static const size_t buffer_size = 64 ;
54+ void MemTracker::initialize () {
55+ bool rc = true ;
56+ assert (_tracking_level == NMT_unknown, " only call once" );
57+
58+ NMT_TrackingLevel level = NMTUtil::parse_tracking_level (NativeMemoryTracking);
59+ // Should have been validated before in arguments.cpp
60+ assert (level == NMT_off || level == NMT_summary || level == NMT_detail,
61+ " Invalid setting for NativeMemoryTracking (%s)" , NativeMemoryTracking);
5162
52- NMT_TrackingLevel MemTracker::init_tracking_level () {
5363 // Memory type is encoded into tracking header as a byte field,
5464 // make sure that we don't overflow it.
5565 STATIC_ASSERT (mt_number_of_types <= max_jubyte);
5666
57- char nmt_env_variable[buffer_size];
58- jio_snprintf (nmt_env_variable, sizeof (nmt_env_variable), " NMT_LEVEL_%d" , os::current_process_id ());
59- const char * nmt_env_value;
60- #ifdef _WINDOWS
61- // Read the NMT environment variable from the PEB instead of the CRT
62- char value[buffer_size];
63- nmt_env_value = GetEnvironmentVariable (nmt_env_variable, value, (DWORD)sizeof (value)) != 0 ? value : NULL ;
64- #else
65- nmt_env_value = ::getenv (nmt_env_variable);
66- #endif
67- NMT_TrackingLevel level = NMT_off;
68- if (nmt_env_value != NULL ) {
69- if (strcmp (nmt_env_value, " summary" ) == 0 ) {
70- level = NMT_summary;
71- } else if (strcmp (nmt_env_value, " detail" ) == 0 ) {
72- level = NMT_detail;
73- } else if (strcmp (nmt_env_value, " off" ) != 0 ) {
74- // The value of the environment variable is invalid
75- _is_nmt_env_valid = false ;
76- }
77- // Remove the environment variable to avoid leaking to child processes
78- os::unsetenv (nmt_env_variable);
79- }
80-
81- if (!MallocTracker::initialize (level) ||
82- !VirtualMemoryTracker::initialize (level)) {
83- level = NMT_off;
84- }
85- return level;
86- }
87-
88- void MemTracker::init () {
89- NMT_TrackingLevel level = tracking_level ();
90- if (level >= NMT_summary) {
91- if (!VirtualMemoryTracker::late_initialize (level) ||
92- !ThreadStackTracker::late_initialize (level)) {
93- shutdown ();
67+ if (level > NMT_off) {
68+ if (!MallocTracker::initialize (level) ||
69+ !VirtualMemoryTracker::initialize (level) ||
70+ !ThreadStackTracker::initialize (level)) {
71+ assert (false , " NMT initialization failed" );
72+ level = NMT_off;
73+ log_warning (nmt)(" NMT initialization failed. NMT disabled." );
9474 return ;
9575 }
9676 }
97- }
9877
99- bool MemTracker::check_launcher_nmt_support (const char * value) {
100- if (strcmp (value, " =detail" ) == 0 ) {
101- if (MemTracker::tracking_level () != NMT_detail) {
102- return false ;
103- }
104- } else if (strcmp (value, " =summary" ) == 0 ) {
105- if (MemTracker::tracking_level () != NMT_summary) {
106- return false ;
107- }
108- } else if (strcmp (value, " =off" ) == 0 ) {
109- if (MemTracker::tracking_level () != NMT_off) {
110- return false ;
111- }
112- } else {
113- _is_nmt_env_valid = false ;
114- }
78+ NMTPreInit::pre_to_post ();
11579
116- return true ;
117- }
80+ _tracking_level = _cmdline_tracking_level = level;
11881
119- bool MemTracker::verify_nmt_option () {
120- return _is_nmt_env_valid;
82+ // Log state right after NMT initialization
83+ if (log_is_enabled (Info, nmt)) {
84+ LogTarget (Info, nmt) lt;
85+ LogStream ls (lt);
86+ ls.print_cr (" NMT initialized: %s" , NMTUtil::tracking_level_to_string (_tracking_level));
87+ ls.print_cr (" Preinit state: " );
88+ NMTPreInit::print_state (&ls);
89+ ls.cr ();
90+ }
12191}
12292
12393void * MemTracker::malloc_base (void * memblock) {
@@ -174,6 +144,8 @@ bool MemTracker::transition_to(NMT_TrackingLevel level) {
174144void MemTracker::error_report (outputStream* output) {
175145 if (tracking_level () >= NMT_summary) {
176146 report (true , output, MemReporterBase::default_scale); // just print summary for error case.
147+ output->print (" Preinit state:" );
148+ NMTPreInit::print_state (output);
177149 }
178150}
179151
@@ -214,9 +186,14 @@ void MemTracker::report(bool summary_only, outputStream* output, size_t scale) {
214186void MemTracker::tuning_statistics (outputStream* out) {
215187 // NMT statistics
216188 out->print_cr (" Native Memory Tracking Statistics:" );
189+ out->print_cr (" State: %s" , NMTUtil::tracking_level_to_string (_tracking_level));
217190 out->print_cr (" Malloc allocation site table size: %d" , MallocSiteTable::hash_buckets ());
218191 out->print_cr (" Tracking stack depth: %d" , NMT_TrackingStackDepth);
219192 NOT_PRODUCT (out->print_cr (" Peak concurrent access: %d" , MallocSiteTable::access_peak_count ());)
220193 out->cr ();
221194 MallocSiteTable::print_tuning_statistics (out);
195+ out->cr ();
196+ out->print_cr (" Preinit state:" );
197+ NMTPreInit::print_state (out);
198+ out->cr ();
222199}
0 commit comments