23
23
*/
24
24
#include " precompiled.hpp"
25
25
#include " jvm.h"
26
+ #include " logging/log.hpp"
27
+ #include " logging/logStream.hpp"
26
28
#include " memory/metaspaceUtils.hpp"
27
29
#include " runtime/atomic.hpp"
30
+ #include " runtime/globals.hpp"
28
31
#include " runtime/orderAccess.hpp"
29
32
#include " runtime/vmThread.hpp"
30
33
#include " runtime/vmOperations.hpp"
31
34
#include " services/memBaseline.hpp"
32
35
#include " services/memReporter.hpp"
33
36
#include " services/mallocTracker.inline.hpp"
34
37
#include " services/memTracker.hpp"
38
+ #include " services/nmtCommon.hpp"
39
+ #include " services/nmtPreInit.hpp"
35
40
#include " services/threadStackTracker.hpp"
36
41
#include " utilities/debug.hpp"
37
42
#include " utilities/defaultStream.hpp"
@@ -45,79 +50,44 @@ volatile NMT_TrackingLevel MemTracker::_tracking_level = NMT_unknown;
45
50
NMT_TrackingLevel MemTracker::_cmdline_tracking_level = NMT_unknown;
46
51
47
52
MemBaseline MemTracker::_baseline;
48
- bool MemTracker::_is_nmt_env_valid = true ;
49
53
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);
51
62
52
- NMT_TrackingLevel MemTracker::init_tracking_level () {
53
63
// Memory type is encoded into tracking header as a byte field,
54
64
// make sure that we don't overflow it.
55
65
STATIC_ASSERT (mt_number_of_types <= max_jubyte);
56
66
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." );
94
74
return ;
95
75
}
96
76
}
97
- }
98
77
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 ();
115
79
116
- return true ;
117
- }
80
+ _tracking_level = _cmdline_tracking_level = level;
118
81
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
+ }
121
91
}
122
92
123
93
void * MemTracker::malloc_base (void * memblock) {
@@ -174,6 +144,8 @@ bool MemTracker::transition_to(NMT_TrackingLevel level) {
174
144
void MemTracker::error_report (outputStream* output) {
175
145
if (tracking_level () >= NMT_summary) {
176
146
report (true , output, MemReporterBase::default_scale); // just print summary for error case.
147
+ output->print (" Preinit state:" );
148
+ NMTPreInit::print_state (output);
177
149
}
178
150
}
179
151
@@ -214,9 +186,14 @@ void MemTracker::report(bool summary_only, outputStream* output, size_t scale) {
214
186
void MemTracker::tuning_statistics (outputStream* out) {
215
187
// NMT statistics
216
188
out->print_cr (" Native Memory Tracking Statistics:" );
189
+ out->print_cr (" State: %s" , NMTUtil::tracking_level_to_string (_tracking_level));
217
190
out->print_cr (" Malloc allocation site table size: %d" , MallocSiteTable::hash_buckets ());
218
191
out->print_cr (" Tracking stack depth: %d" , NMT_TrackingStackDepth);
219
192
NOT_PRODUCT (out->print_cr (" Peak concurrent access: %d" , MallocSiteTable::access_peak_count ());)
220
193
out->cr ();
221
194
MallocSiteTable::print_tuning_statistics (out);
195
+ out->cr ();
196
+ out->print_cr (" Preinit state:" );
197
+ NMTPreInit::print_state (out);
198
+ out->cr ();
222
199
}
0 commit comments