]> granicus.if.org Git - sysstat/commitdiff
sadf: PCP: Add support for A_MEMORY activity
authorSebastien GODARD <sysstat@users.noreply.github.com>
Wed, 20 Mar 2019 09:47:23 +0000 (10:47 +0100)
committerSebastien GODARD <sysstat@users.noreply.github.com>
Wed, 20 Mar 2019 09:47:23 +0000 (10:47 +0100)
Add metrics displayed by "sar -r [ALL]" (memory statistics) to PCP
archive.

Signed-off-by: Sebastien GODARD <sysstat@users.noreply.github.com>
activity.c
pcp_def_metrics.c
pcp_def_metrics.h
pcp_stats.c
pcp_stats.h
sadf_misc.c

index 6a76f3997f43221940268f9d2db9873656330aec..e7c1504b4bd3bf27b1376bb0b035fb79b3f9e1e3 100644 (file)
@@ -367,6 +367,7 @@ struct activity memory_act = {
        .f_json_print   = json_print_memory_stats,
        .f_svg_print    = svg_print_memory_stats,
        .f_raw_print    = raw_print_memory_stats,
+       .f_pcp_print    = pcp_print_memory_stats,
        .f_count_new    = NULL,
        .item_list      = NULL,
        .desc           = "Memory and/or swap utilization",
index fd96cf43138ddeb1ca30c8c9063e048993cb2088..2c9f552b910d3f7a60ba38791005b6944eee4734 100644 (file)
@@ -165,6 +165,112 @@ void pcp_def_pcsw_metrics(void)
 #endif /* HAVE_PCP */
 }
 
+/*
+ ***************************************************************************
+ * Define PCP metrics for memory statistics.
+ *
+ * IN:
+ * @a          Activity structure with statistics.
+ ***************************************************************************
+ */
+void pcp_def_memory_metrics(struct activity *a)
+{
+#ifdef HAVE_PCP
+       if (DISPLAY_MEMORY(a->opt_flags)) {
+
+               pmiAddMetric("mem.util.free",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.available",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.used",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.used_pct",
+                            PM_IN_NULL, PM_TYPE_FLOAT, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(0, 0, 0, 0, 0, 0));
+
+               pmiAddMetric("mem.util.buffers",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.cached",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.commit",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.commit_pct",
+                            PM_IN_NULL, PM_TYPE_FLOAT, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(0, 0, 0, 0, 0, 0));
+
+               pmiAddMetric("mem.util.active",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.inactive",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.dirty",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               if (DISPLAY_MEM_ALL(a->opt_flags)) {
+
+                       pmiAddMetric("mem.util.anonpages",
+                                    PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                                    pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+                       pmiAddMetric("mem.util.slab",
+                                    PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                                    pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+                       pmiAddMetric("mem.util.stack",
+                                    PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                                    pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+                       pmiAddMetric("mem.util.pageTables",
+                                    PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                                    pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+                       pmiAddMetric("mem.util.vmused",
+                                    PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                                    pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+               }
+       }
+
+       if (DISPLAY_SWAP(a->opt_flags)) {
+
+               pmiAddMetric("mem.util.swapFree",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.swapUsed",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.swapUsed_pct",
+                            PM_IN_NULL, PM_TYPE_FLOAT, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(0, 0, 0, 0, 0, 0));
+
+               pmiAddMetric("mem.util.swapCached",
+                            PM_IN_NULL, PM_TYPE_U64, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(1, 0, 0, 0, PM_SPACE_KBYTE, 0));
+
+               pmiAddMetric("mem.util.swapCached_pct",
+                            PM_IN_NULL, PM_TYPE_FLOAT, PM_INDOM_NULL, PM_SEM_INSTANT,
+                            pmiUnits(0, 0, 0, 0, 0, 0));
+       }
+#endif /* HAVE_PCP */
+}
+
 /*
  ***************************************************************************
  * Define PCP metrics for queue and load statistics.
index fc895268fd9b3b0cb2ff50f4c9623456ca6e13c8..c54c1fd1fbd9fb8f8c488146f0ee804aeb745f4c 100644 (file)
@@ -14,6 +14,7 @@
 
 void pcp_def_cpu_metrics(struct activity *);
 void pcp_def_pcsw_metrics(void);
+void pcp_def_memory_metrics(struct activity *);
 void pcp_def_queue_metrics(void);
 
 #endif /* _PCP_DEF_METRICS_H */
index 5fa818e32a7dc4db485d8203151d7947c3883033..756892abf418e3f9d1f9e451ece4ce149477901d 100644 (file)
@@ -211,6 +211,111 @@ __print_funct_t pcp_print_pcsw_stats(struct activity *a, int curr, unsigned long
 #endif /* HAVE_PCP */
 }
 
+/*
+ ***************************************************************************
+ * Display memory statistics in PCP format.
+ *
+ * IN:
+ * @a          Activity structure with statistics.
+ * @curr       Index in array for current sample statistics.
+ * @itv                Interval of time in 1/100th of a second.
+ * @record_hdr Record header for current sample.
+ ***************************************************************************
+ */
+__print_funct_t pcp_print_memory_stats(struct activity *a, int curr, unsigned long long itv,
+                                      struct record_header *record_hdr)
+{
+#ifdef HAVE_PCP
+       char buf[64];
+       struct stats_memory
+               *smc = (struct stats_memory *) a->buf[curr];
+       unsigned long long nousedmem;
+
+       if (DISPLAY_MEMORY(a->opt_flags)) {
+
+               nousedmem = smc->frmkb + smc->bufkb + smc->camkb + smc->slabkb;
+               if (nousedmem > smc->tlmkb) {
+                       nousedmem = smc->tlmkb;
+               }
+
+               snprintf(buf, sizeof(buf), "%llu", smc->frmkb);
+               pmiPutValue("mem.util.free", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->availablekb);
+               pmiPutValue("mem.util.available", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->tlmkb - nousedmem);
+               pmiPutValue("mem.util.used", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%f",
+                        smc->tlmkb ? SP_VALUE(nousedmem, smc->tlmkb, smc->tlmkb) : 0.0);
+               pmiPutValue("mem.util.used_pct", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->bufkb);
+               pmiPutValue("mem.util.buffers", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->camkb);
+               pmiPutValue("mem.util.cached", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->comkb);
+               pmiPutValue("mem.util.commit", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%f",
+                        (smc->tlmkb + smc->tlskb) ? SP_VALUE(0, smc->comkb, smc->tlmkb + smc->tlskb)
+                                                  : 0.0);
+               pmiPutValue("mem.util.commit_pct", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->activekb);
+               pmiPutValue("mem.util.active", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->inactkb);
+               pmiPutValue("mem.util.inactive", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->dirtykb);
+               pmiPutValue("mem.util.dirty", NULL, buf);
+
+               if (DISPLAY_MEM_ALL(a->opt_flags)) {
+
+                       snprintf(buf, sizeof(buf), "%llu", smc->anonpgkb);
+                       pmiPutValue("mem.util.anonpages", NULL, buf);
+
+                       snprintf(buf, sizeof(buf), "%llu", smc->slabkb);
+                       pmiPutValue("mem.util.slab", NULL, buf);
+
+                       snprintf(buf, sizeof(buf), "%llu", smc->kstackkb);
+                       pmiPutValue("mem.util.stack", NULL, buf);
+
+                       snprintf(buf, sizeof(buf), "%llu", smc->pgtblkb);
+                       pmiPutValue("mem.util.pageTables", NULL, buf);
+
+                       snprintf(buf, sizeof(buf), "%llu", smc->vmusedkb);
+                       pmiPutValue("mem.util.vmused", NULL, buf);
+               }
+       }
+
+       if (DISPLAY_SWAP(a->opt_flags)) {
+
+               snprintf(buf, sizeof(buf), "%llu", smc->frskb);
+               pmiPutValue("mem.util.swapFree", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->tlskb - smc->frskb);
+               pmiPutValue("mem.util.swapUsed", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%f",
+                        smc->tlskb ? SP_VALUE(smc->frskb, smc->tlskb, smc->tlskb) : 0.0);
+               pmiPutValue("mem.util.swapUsed_pct", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%llu", smc->caskb);
+               pmiPutValue("mem.util.swapCached", NULL, buf);
+
+               snprintf(buf, sizeof(buf), "%f",
+                        (smc->tlskb - smc->frskb) ? SP_VALUE(0, smc->caskb, smc->tlskb - smc->frskb)
+                                                  : 0.0);
+               pmiPutValue("mem.util.swapCached_pct", NULL, buf);
+       }
+#endif /* HAVE_PCP */
+}
+
 /*
  ***************************************************************************
  * Display queue and load statistics in PCP format
index 1e266aee7c247257bb43c51afe37c77124a3aaa8..b73fb1794b3db404f44900bd6a7cddf634bb5156 100644 (file)
@@ -17,6 +17,8 @@ __print_funct_t pcp_print_cpu_stats
        (struct activity *, int, unsigned long long, struct record_header *);
 __print_funct_t pcp_print_pcsw_stats
        (struct activity *, int, unsigned long long, struct record_header *);
+__print_funct_t pcp_print_memory_stats
+       (struct activity *, int, unsigned long long, struct record_header *);
 __print_funct_t pcp_print_queue_stats
        (struct activity *, int, unsigned long long, struct record_header *);
 
index 9acf2aef8e1b5ef318c95bb9fed9004f88bcf3e1..ef124dec0d48d082b089274b5673eca41a6e35de 100644 (file)
@@ -505,6 +505,10 @@ __printf_funct_t print_pcp_statistics(int *tab, int action, struct activity *act
                                        pcp_def_pcsw_metrics();
                                        break;
 
+                               case A_MEMORY:
+                                       pcp_def_memory_metrics(act[p]);
+                                       break;
+
                                case A_QUEUE:
                                        pcp_def_queue_metrics();
                                        break;