@cryptotaxi247 / netdata-1 / commits / 714ed1454

cgroups now also read usage_in_bytes, memsw_usage_in_bytes, failcnt and creates 2 new memory charts; fixes #1019

Costa Tsaousis (ktsaou) committed Oct 1, 2016 at 03:14 UTC 714ed145493daf78847907328b44d78779347ff9
4 files changed +104 -2
src/common.c
+17
@@ -1126,3 +1126,20 @@ void get_system_HZ(void) {
1126
1127 hz = (unsigned int) ticks;
1128 }
1129 +
1130 +int read_single_number_file(const char *filename, unsigned long long *result) {
1131 + char buffer[1024 + 1];
1132 +
1133 + int fd = open(filename, O_RDONLY, 0666);
1134 + if(unlikely(fd == -1)) return 1;
1135 +
1136 + ssize_t r = read(fd, buffer, 1024);
1137 + if(unlikely(r == -1)) {
1138 + close(fd);
1139 + return 2;
1140 + }
1141 +
1142 + close(fd);
1143 + *result = strtoull(buffer, NULL, 0);
1144 + return 0;
1145 +}
src/common.h
+2
@@ -184,4 +184,6 @@ extern void get_system_HZ(void);
184 #endif
185 #endif
186
187 +extern int read_single_number_file(const char *filename, unsigned long long *result);
188 +
189 #endif /* NETDATA_COMMON_H */
src/sys_fs_cgroup.c
+84 -1
@@ -138,6 +138,18 @@ struct memory {
138 unsigned long long total_active_file;
139 unsigned long long total_unevictable;
140 */
141 +
142 + int usage_in_bytes_updated;
143 + char *filename_usage_in_bytes;
144 + unsigned long long usage_in_bytes;
145 +
146 + int msw_usage_in_bytes_updated;
147 + char *filename_msw_usage_in_bytes;
148 + unsigned long long msw_usage_in_bytes;
149 +
150 + int failcnt_updated;
151 + char *filename_failcnt;
152 + unsigned long long failcnt;
153 };
154
155 // https://www.kernel.org/doc/Documentation/cgroup-v1/cpuacct.txt
@@ -557,6 +569,24 @@ void cgroup_read_memory(struct memory *mem) {
569
570 mem->updated = 1;
571 }
572 +
573 + mem->usage_in_bytes_updated = 0;
574 + if(mem->filename_usage_in_bytes) {
575 + if(likely(!read_single_number_file(mem->filename_usage_in_bytes, &mem->usage_in_bytes)))
576 + mem->usage_in_bytes_updated = 1;
577 + }
578 +
579 + mem->msw_usage_in_bytes_updated = 0;
580 + if(mem->filename_msw_usage_in_bytes) {
581 + if(likely(!read_single_number_file(mem->filename_msw_usage_in_bytes, &mem->msw_usage_in_bytes)))
582 + mem->msw_usage_in_bytes_updated = 1;
583 + }
584 +
585 + mem->failcnt_updated = 0;
586 + if(mem->filename_failcnt) {
587 + if(likely(!read_single_number_file(mem->filename_failcnt, &mem->failcnt)))
588 + mem->failcnt_updated = 1;
589 + }
590 }
591
592 void cgroup_read(struct cgroup *cg) {
@@ -990,6 +1020,27 @@ void find_all_cgroups() {
1020 debug(D_CGROUP, "memory.stat filename for cgroup '%s': '%s'", cg->id, cg->memory.filename);
1021 }
1022 else debug(D_CGROUP, "memory.stat file for cgroup '%s': '%s' does not exist.", cg->id, filename);
1023 +
1024 + snprintfz(filename, FILENAME_MAX, "%s%s/memory.usage_in_bytes", cgroup_memory_base, cg->id);
1025 + if(stat(filename, &buf) != -1) {
1026 + cg->memory.filename_usage_in_bytes = strdupz(filename);
1027 + debug(D_CGROUP, "memory.usage_in_bytes filename for cgroup '%s': '%s'", cg->id, cg->memory.filename_usage_in_bytes);
1028 + }
1029 + else debug(D_CGROUP, "memory.usage_in_bytes file for cgroup '%s': '%s' does not exist.", cg->id, filename);
1030 +
1031 + snprintfz(filename, FILENAME_MAX, "%s%s/memory.msw_usage_in_bytes", cgroup_memory_base, cg->id);
1032 + if(stat(filename, &buf) != -1) {
1033 + cg->memory.filename_msw_usage_in_bytes = strdupz(filename);
1034 + debug(D_CGROUP, "memory.msw_usage_in_bytes filename for cgroup '%s': '%s'", cg->id, cg->memory.filename_msw_usage_in_bytes);
1035 + }
1036 + else debug(D_CGROUP, "memory.msw_usage_in_bytes file for cgroup '%s': '%s' does not exist.", cg->id, filename);
1037 +
1038 + snprintfz(filename, FILENAME_MAX, "%s%s/memory.failcnt", cgroup_memory_base, cg->id);
1039 + if(stat(filename, &buf) != -1) {
1040 + cg->memory.filename_failcnt = strdupz(filename);
1041 + debug(D_CGROUP, "memory.failcnt filename for cgroup '%s': '%s'", cg->id, cg->memory.filename_failcnt);
1042 + }
1043 + else debug(D_CGROUP, "memory.failcnt file for cgroup '%s': '%s' does not exist.", cg->id, filename);
1044 }
1045 if(cgroup_enable_blkio) {
1046 if(!cg->io_service_bytes.filename) {
@@ -1118,7 +1169,7 @@ void update_cgroup_charts(int update_every) {
1169 st = rrdset_find_bytype(type, "mem");
1170 if(!st) {
1171 snprintfz(title, CHART_TITLE_MAX, "Memory Usage for cgroup %s", cg->chart_title);
1121 - st = rrdset_create(type, "mem", NULL, "mem", "cgroup.mem", title, "MB", 40200, update_every,
1172 + st = rrdset_create(type, "mem", NULL, "mem", "cgroup.mem", title, "MB", 40210, update_every,
1173 RRDSET_TYPE_STACKED);
1174
1175 rrddim_add(st, "cache", NULL, 1, 1024 * 1024, RRDDIM_ABSOLUTE);
@@ -1191,6 +1242,38 @@ void update_cgroup_charts(int update_every) {
1242 }
1243 }
1244
1245 + if(cg->memory.usage_in_bytes_updated) {
1246 + st = rrdset_find_bytype(type, "mem_usage");
1247 + if(!st) {
1248 + snprintfz(title, CHART_TITLE_MAX, "Total Memory for cgroup %s", cg->chart_title);
1249 + st = rrdset_create(type, "mem_usage", NULL, "mem", "cgroup.mem_usage", title, "MB", 40200,
1250 + update_every, RRDSET_TYPE_STACKED);
1251 +
1252 + rrddim_add(st, "ram", NULL, 1, 1024 * 1024, RRDDIM_ABSOLUTE);
1253 + rrddim_add(st, "swap", NULL, 1, 1024 * 1024, RRDDIM_ABSOLUTE);
1254 + }
1255 + else rrdset_next(st);
1256 +
1257 + rrddim_set(st, "ram", cg->memory.usage_in_bytes);
1258 + rrddim_set(st, "swap", (cg->memory.msw_usage_in_bytes > cg->memory.usage_in_bytes)?cg->memory.msw_usage_in_bytes - cg->memory.usage_in_bytes:0);
1259 + rrdset_done(st);
1260 + }
1261 +
1262 + if(cg->memory.failcnt_updated && cg->memory.failcnt > 0) {
1263 + st = rrdset_find_bytype(type, "mem_failcnt");
1264 + if(!st) {
1265 + snprintfz(title, CHART_TITLE_MAX, "Memory Limit Failures for cgroup %s", cg->chart_title);
1266 + st = rrdset_create(type, "mem_failcnt", NULL, "mem", "cgroup.mem_failcnt", title, "MB", 40250,
1267 + update_every, RRDSET_TYPE_LINE);
1268 +
1269 + rrddim_add(st, "failures", NULL, 1, 1, RRDDIM_INCREMENTAL);
1270 + }
1271 + else rrdset_next(st);
1272 +
1273 + rrddim_set(st, "failures", cg->memory.failcnt);
1274 + rrdset_done(st);
1275 + }
1276 +
1277 if(cg->io_service_bytes.updated && cg->io_service_bytes.Read + cg->io_service_bytes.Write > 0) {
1278 st = rrdset_find_bytype(type, "io");
1279 if(!st) {
web/dashboard.css
+1 -1
@@ -209,7 +209,7 @@ body {
209 outline: thin dotted;
210 }
211 .netdata-legend-series > .netdata-legend-series-content::-webkit-scrollbar {
212 - display: block; /* was 'none', but chrome was hidding content with it */
212 + display: block; /* was 'none', but chrome was hiding content with it */
213 }
214 .has-scrollbar > .netdata-legend-series-content::-webkit-scrollbar {
215 display: block;