55#include < malloc.h>
66#endif
77
8- #include < fstream>
8+ #include < charconv>
9+
10+ #include " common/fmt_common.h"
11+
912
1013#define dout_subsys ceph_subsys_
1114
@@ -17,45 +20,21 @@ MemoryModel::MemoryModel(CephContext *cct_)
1720{
1821}
1922
20- void MemoryModel::_sample ( mem_snap_t *psnap )
23+ std::optional< int64_t > MemoryModel::get_mapped_heap ( )
2124{
22- ifstream f;
23-
24- f.open (PROCPREFIX " /proc/self/status" );
25- if (!f.is_open ()) {
26- ldout (cct, 0 ) << " check_memory_usage unable to open " PROCPREFIX " /proc/self/status" << dendl;
27- return ;
25+ if (!proc_maps.is_open ()) {
26+ ldout (cct, 0 ) << fmt::format (" MemoryModel::get_mapped_heap() unable to open {}" , proc_maps_fn) << dendl;
27+ return std::nullopt ;
2828 }
29- while (!f.eof ()) {
30- string line;
31- getline (f, line);
32-
33- if (strncmp (line.c_str (), " VmSize:" , 7 ) == 0 )
34- psnap->size = atol (line.c_str () + 7 );
35- else if (strncmp (line.c_str (), " VmRSS:" , 6 ) == 0 )
36- psnap->rss = atol (line.c_str () + 7 );
37- else if (strncmp (line.c_str (), " VmHWM:" , 6 ) == 0 )
38- psnap->hwm = atol (line.c_str () + 7 );
39- else if (strncmp (line.c_str (), " VmLib:" , 6 ) == 0 )
40- psnap->lib = atol (line.c_str () + 7 );
41- else if (strncmp (line.c_str (), " VmPeak:" , 7 ) == 0 )
42- psnap->peak = atol (line.c_str () + 7 );
43- else if (strncmp (line.c_str (), " VmData:" , 7 ) == 0 )
44- psnap->data = atol (line.c_str () + 7 );
45- }
46- f.close ();
29+ // always rewind before reading
30+ proc_maps.clear ();
31+ proc_maps.seekg (0 );
4732
48- f.open (PROCPREFIX " /proc/self/maps" );
49- if (!f.is_open ()) {
50- ldout (cct, 0 ) << " check_memory_usage unable to open " PROCPREFIX " /proc/self/maps" << dendl;
51- return ;
52- }
33+ int64_t heap = 0 ;
5334
54- long heap = 0 ;
55- while (f.is_open () && !f.eof ()) {
35+ while (proc_maps.is_open () && !proc_maps.eof ()) {
5636 string line;
57- getline (f, line);
58- // ldout(cct, 0) << "line is " << line << dendl;
37+ getline (proc_maps, line);
5938
6039 const char *start = line.c_str ();
6140 const char *dash = start;
@@ -69,8 +48,6 @@ void MemoryModel::_sample(mem_snap_t *psnap)
6948 unsigned long long as = strtoll (start, 0 , 16 );
7049 unsigned long long ae = strtoll (dash+1 , 0 , 16 );
7150
72- // ldout(cct, 0) << std::hex << as << " to " << ae << std::dec << dendl;
73-
7451 end++;
7552 const char *mode = end;
7653
@@ -83,7 +60,6 @@ void MemoryModel::_sample(mem_snap_t *psnap)
8360 end++;
8461
8562 long size = ae - as;
86- // ldout(cct, 0) << "size " << size << " mode is '" << mode << "' end is '" << end << "'" << dendl;
8763
8864 /*
8965 * anything 'rw' and anon is assumed to be heap.
@@ -92,6 +68,39 @@ void MemoryModel::_sample(mem_snap_t *psnap)
9268 heap += size;
9369 }
9470
95- psnap->heap = heap >> 10 ;
71+ return heap;
72+ }
73+
74+
75+
76+ void MemoryModel::_sample (mem_snap_t *psnap)
77+ {
78+ if (!proc_status.is_open ()) {
79+ ldout (cct, 0 ) << fmt::format (" MemoryModel::sample() unable to open {}" , proc_stat_fn) << dendl;
80+ return ;
81+ }
82+ // always rewind before reading
83+ proc_status.clear ();
84+ proc_status.seekg (0 );
85+
86+ while (!proc_status.eof ()) {
87+ string line;
88+ getline (proc_status, line);
89+
90+ if (strncmp (line.c_str (), " VmSize:" , 7 ) == 0 )
91+ psnap->size = atol (line.c_str () + 7 );
92+ else if (strncmp (line.c_str (), " VmRSS:" , 6 ) == 0 )
93+ psnap->rss = atol (line.c_str () + 7 );
94+ else if (strncmp (line.c_str (), " VmHWM:" , 6 ) == 0 )
95+ psnap->hwm = atol (line.c_str () + 7 );
96+ else if (strncmp (line.c_str (), " VmLib:" , 6 ) == 0 )
97+ psnap->lib = atol (line.c_str () + 7 );
98+ else if (strncmp (line.c_str (), " VmPeak:" , 7 ) == 0 )
99+ psnap->peak = atol (line.c_str () + 7 );
100+ else if (strncmp (line.c_str (), " VmData:" , 7 ) == 0 )
101+ psnap->data = atol (line.c_str () + 7 );
102+ }
96103
104+ // get heap size
105+ psnap->heap = static_cast <long >(get_mapped_heap ().value_or (0 ));
97106}
0 commit comments