* collectd - src/swap.c
* Copyright (C) 2005-2009 Florian octo Forster
* Copyright (C) 2009 Stefan Völkel
+ * Copyright (C) 2009 Manuel Sanmartin
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
*
* Authors:
* Florian octo Forster <octo at verplant.org>
+ * Manuel Sanmartin
**/
#if HAVE_CONFIG_H
# include <statgrab.h>
#endif
+#if HAVE_PERFSTAT
+# include <sys/protosw.h>
+# include <libperfstat.h>
+#endif
+
#undef MAX
#define MAX(x,y) ((x) > (y) ? (x) : (y))
/* No global variables */
/* #endif HAVE_LIBSTATGRAB */
+#elif HAVE_PERFSTAT
+static int pagesize;
+static perfstat_memory_total_t pmemory;
+/*# endif HAVE_PERFSTAT */
+
#else
# error "No applicable input method."
#endif /* HAVE_LIBSTATGRAB */
#elif HAVE_LIBSTATGRAB
/* No init stuff */
-#endif /* HAVE_LIBSTATGRAB */
+/* #endif HAVE_LIBSTATGRAB */
+
+#elif HAVE_PERFSTAT
+ pagesize = getpagesize();
+#endif /* HAVE_PERFSTAT */
return (0);
}
#if KERNEL_LINUX
FILE *fh;
char buffer[1024];
-
+
char *fields[8];
int numfields;
+ _Bool old_kernel=0;
+
derive_t swap_used = 0;
derive_t swap_cached = 0;
derive_t swap_free = 0;
if ((fh = fopen ("/proc/vmstat", "r")) == NULL)
{
- char errbuf[1024];
- WARNING ("swap: fopen: %s",
- sstrerror (errno, errbuf, sizeof (errbuf)));
- return (-1);
+ // /proc/vmstat does not exist in kernels <2.6
+ if ((fh = fopen ("/proc/stat", "r")) == NULL )
+ {
+ char errbuf[1024];
+ WARNING ("swap: fopen: %s",
+ sstrerror (errno, errbuf, sizeof (errbuf)));
+ return (-1);
+ }
+ else
+ old_kernel = 1;
}
while (fgets (buffer, 1024, fh) != NULL)
{
- derive_t *val = NULL;
-
- if (strncasecmp (buffer, "pswpin", 6) == 0)
- val = &swap_in;
- else if (strncasecmp (buffer, "pswpout", 7) == 0)
- val = &swap_out;
- else
- continue;
-
- numfields = strsplit (buffer, fields, 8);
-
- if (numfields < 2)
- continue;
-
- *val = (derive_t) atoll (fields[1]);
- }
+ numfields = strsplit (buffer, fields, STATIC_ARRAY_SIZE (fields));
+
+ if (!old_kernel)
+ {
+ if (numfields != 2)
+ continue;
+
+ if (strcasecmp ("pswpin", fields[0]) != 0)
+ strtoderive (fields[1], &swap_in);
+ else if (strcasecmp ("pswpout", fields[0]) == 0)
+ strtoderive (fields[1], &swap_out);
+ }
+ else /* if (old_kernel) */
+ {
+ if (numfields != 3)
+ continue;
+
+ if (strcasecmp ("page", fields[0]) == 0)
+ {
+ strtoderive (fields[1], &swap_in);
+ strtoderive (fields[2], &swap_out);
+ }
+ }
+ } /* while (fgets) */
if (fclose (fh))
{
swap_submit ("cached", swap_cached, DS_TYPE_GAUGE);
swap_submit ("in", swap_in, DS_TYPE_DERIVE);
swap_submit ("out", swap_out, DS_TYPE_DERIVE);
-
/* #endif KERNEL_LINUX */
#elif HAVE_LIBKSTAT
* However, Solaris does not allow to allocated/reserved more than the
* available swap (physical memory + disk swap), so the pedant may
* prefer: allocated + unallocated = reserved, available
- *
+ *
* We map the above to: used + resv = n/a, free
*
* Does your brain hurt yet? - Christophe Kalt
swap_submit ("used", (derive_t) swap->used, DS_TYPE_GAUGE);
swap_submit ("free", (derive_t) swap->free, DS_TYPE_GAUGE);
-#endif /* HAVE_LIBSTATGRAB */
+/* #endif HAVE_LIBSTATGRAB */
+
+#elif HAVE_PERFSTAT
+ if(perfstat_memory_total(NULL, &pmemory, sizeof(perfstat_memory_total_t), 1) < 0)
+ {
+ char errbuf[1024];
+ WARNING ("memory plugin: perfstat_memory_total failed: %s",
+ sstrerror (errno, errbuf, sizeof (errbuf)));
+ return (-1);
+ }
+ swap_submit ("used", (derive_t) (pmemory.pgsp_total - pmemory.pgsp_free) * pagesize, DS_TYPE_GAUGE);
+ swap_submit ("free", (derive_t) pmemory.pgsp_free * pagesize , DS_TYPE_GAUGE);
+#endif /* HAVE_PERFSTAT */
return (0);
} /* int swap_read */