[Xymon] Patch for vmstat processing for FreeBSD

Brian Scott Brian.Scott at bunyatech.com.au
Thu Jul 1 07:19:22 CEST 2021


Hi,

Another patch that I wanted to keep apart from the others I've just 
posted because it isn't really related.

I seem to have 2 problems when dealing with vmstat output from FreeBSD.

* Unknown variable disk_fd0 when updating the rrd.

* Insufficient columns of data provided.

I'm not sure if anything cares about data from vmstat or if it's just 
stamp collecting. The data doesn't have much value. The messages are 
annoying though.

Anyway, the problem is that the FreeBSD vmstat command has a variable 
number of disks displayed. In early versions of FreeBSD (5 and earlier) 
there were a maximum of 3 devices selected and now (6 and later) there 
is a maximum of 2. The problem occurs when there aren't that many 
devices attached. The system will pick any junk it can find to make up 
the numbers (e.g. pass0) but when that fails, it just displays less devices.

On a virtual system you will commonly only have one disk device 
attached. No CDs. No Floppy disks. If the attached disk doesn't attach 
through the CAM layer, there won't be a pass0 device created (it's not 
really a disk anyway). I have a few virtual systems running using a 
virtual block device (vtbd) as the only device attached. vmstat can't 
make anything up so only displays one device.

What this means is that there are no guarantees that you will have the 
same number of devices on a given system from time to time as devices 
come and go. It also means that apart from the first disk which will be 
the main system disk, the actual device types may vary from time to 
time. They are essentially worthless.

On a server with many disks attached, you will only see the first 2 so 
the data is incomplete.

My approach has been to ignore all but the first disk and discard the 
rest, whether there be 0, 1 or 2 extras. No good for multi-disk servers, 
but then it wasn't anyway. I also cleaned up the column ordering stuff 
for older systems because it was wrong according to old man pages. 
Nobody will have a FreeBSD 4 or older system to test this on though.

I'd be interested to know if other systems have variable behaviour like 
this in their vmstat processing that should be addressed. FreeBSD had 
special treatment in the code dating back to the transition from the 
maximum of 3 devices to 2.

As I said before, I don't know if anything takes this data seriously. 
There is mention in the file about LARRD compatibility but that seems to 
be really ancient compatibility that I couldn't check.


Cheers,

Brian Scott

-------------- next part --------------
--- xymond/rrd/do_vmstat.c.orig	2019-05-04 08:42:00.000000000 +1000
+++ xymond/rrd/do_vmstat.c	2021-06-29 18:06:50.307658000 +1000
@@ -116,7 +116,8 @@
 	{ -1, NULL }
 };
 
-/* This one matches FreeBSD 4.10 */
+/* This one matches FreeBSD 4.10 and 5.* - Maximum of three disks */
+/* https://www.freebsd.org/cgi/man.cgi?query=vmstat&apropos=0&sektion=8&manpath=FreeBSD+4.10-RELEASE&arch=default&format=html */
 /* LARRD 0.43c compatible */
 static vmstat_layout_t vmstat_freebsd4_layout[] = {
 	{ 0, "cpu_r" },
@@ -131,16 +132,16 @@
 	{ 9, "mem_fr" },
 	{ 10, "sr" },
 	{ 11, "dsk_da0" },
-	{ 12, "dsk_fd0" },
-	{ 13, "cpu_int" },
-	{ 15, "cpu_csw" },
-	{ 16, "cpu_sys" },
-	{ 17, "cpu_usr" },
-	{ 18, "cpu_idl" },
+	{ 14, "cpu_int" },
+	{ 15, "cpu_syc" },
+	{ 16, "cpu_csw" },
+	{ 17, "cpu_sys" },
+	{ 18, "cpu_usr" },
+	{ 19, "cpu_idl" },
 	{ -1, NULL }
 };
 
-/* FreeBSD v6 and later, possibly v5 also */
+/* FreeBSD v6 and later - Maximum of two disks */
 static vmstat_layout_t vmstat_freebsd_layout[] = {
 	{ 0, "cpu_r" },
 	{ 1, "cpu_b" },
@@ -154,7 +155,6 @@
 	{ 9, "mem_fr" },
 	{ 10, "sr" },
 	{ 11, "dsk_da0" },
-	{ 12, "dsk_pa0" },
 	{ 13, "cpu_int" },
 	{ 14, "cpu_syc" },
 	{ 15, "cpu_csw" },
@@ -164,6 +164,29 @@
 	{ -1, NULL }
 };
 
+/* FreeBSD, when there is only one disk device */
+static vmstat_layout_t vmstat_freebsd_short_layout[] = {
+	{ 0, "cpu_r" },
+	{ 1, "cpu_b" },
+	{ 2, "cpu_w" },
+	{ 3, "mem_avm" },
+	{ 4, "mem_free" },
+	{ 5, "mem_flt" },
+	{ 6, "mem_re" },
+	{ 7, "mem_pi" },
+	{ 8, "mem_po" },
+	{ 9, "mem_fr" },
+	{ 10, "sr" },
+	{ 11, "dsk_da0" },
+	{ 12, "cpu_int" },
+	{ 13, "cpu_syc" },
+	{ 14, "cpu_csw" },
+	{ 15, "cpu_usr" },
+	{ 16, "cpu_sys" },
+	{ 17, "cpu_idl" },
+	{ -1, NULL }
+};
+
 /* This one matches NetBSD 2.0 */
 /* LARRD 0.43c does not support NetBSD */
 static vmstat_layout_t vmstat_netbsd_layout[] = {
@@ -419,16 +442,17 @@
 		layout = vmstat_hpux_layout; break;
 	  case OS_FREEBSD:
 		/* 
-		 * Special, because there are two layouts for FreeBSD
-		 * FreeBSD v4.x has 19 fields, later versions of FreeBSD
-		 * are the same as OpenBSD, with 18 fields.
+		 * Special, because there are two or three layouts for FreeBSD
+		 * FreeBSD v4.x has 20 fields, later versions of FreeBSD
+		 * are sometimes the same as OpenBSD, with 19 fields. Or not.
+		 * If there are less disk type devices there will be less fields.
 		 */
 		{
 			char **dsnames = NULL;
 			int dscount, i;
 
 			dscount = rrddatasets(hostname, &dsnames);
-			layout = ((dscount == 19) ? vmstat_freebsd4_layout : vmstat_freebsd_layout);
+			layout = ((dscount == 20) ? vmstat_freebsd4_layout : (dscount == 19) ? vmstat_freebsd_layout : vmstat_freebsd_short_layout);
 
 			if ((dscount > 0) && dsnames) {
 				/* Free the dsnames list */


More information about the Xymon mailing list