Module Name:    src
Committed By:   kre
Date:           Mon Aug  8 16:50:35 UTC 2022

Modified Files:
        src/bin/df: df.1 df.c

Log Message:
Add 4 new flags:
        -b (from FreeBSD) - set blocksize to blocks (512 bytes)
                (overrides a contrary setting in BLOCKSIZE)
        -H (from FreeBSD and Linux): -h using SI units (powers of 10).  Ugh.
        -N suppress the header line (except with -P which requires it).
        -f show only free space (or inodes) in a minimal format (implies -N)
                (that is, with one file[system] specified, print 1 number only)
                With -c, show only the total.
                Intended to be useful for scripting (aka, I needed it.)

While here, improve the usage message (group options where they apply,
there is no reason, for example, that -g should be shown differently
to -k -m ..., and those options aren't at all useful with -G)

Update the man page to match.


To generate a diff of this commit:
cvs rdiff -u -r1.56 -r1.57 src/bin/df/df.1
cvs rdiff -u -r1.99 -r1.100 src/bin/df/df.c

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/bin/df/df.1
diff -u src/bin/df/df.1:1.56 src/bin/df/df.1:1.57
--- src/bin/df/df.1:1.56	Wed Jan  6 20:38:09 2021
+++ src/bin/df/df.1	Mon Aug  8 16:50:35 2022
@@ -1,5 +1,3 @@
-.\"	$NetBSD: df.1,v 1.56 2021/01/06 20:38:09 ginsbach Exp $
-.\"
 .\" Copyright (c) 1989, 1990, 1993
 .\"	The Regents of the University of California.  All rights reserved.
 .\"
@@ -29,7 +27,7 @@
 .\"
 .\"	@(#)df.1	8.2 (Berkeley) 1/13/92
 .\"
-.Dd January 2, 2021
+.Dd August 8, 2022
 .Dt DF 1
 .Os
 .Sh NAME
@@ -37,10 +35,10 @@
 .Nd display free disk space
 .Sh SYNOPSIS
 .Nm
-.Op Fl acglnW
-.Op Fl Ghkm | Fl ihkm | Fl Pk
+.Op Fl aclnW
+.Op Fl G | Fl Pbk | Fl bfgHhikmN
 .Op Fl t Ar type
-.Op Ar file | Ar file_system ...
+.Oo Ar file | Ar file_system Oc Ns ...
 .Sh DESCRIPTION
 .Nm
 displays statistics about the amount of free disk space on the specified
@@ -52,8 +50,12 @@ By default, all sizes are reported in 51
 If neither a file or a
 .Ar file_system
 operand is specified,
-statistics for all mounted file systems are displayed
+statistics for all mounted,
+and not hidden (i.e.: not mounted with
+.Dv MNT_IGNORE ) ,
+file systems are displayed
 (subject to the
+.Fl a ,
 .Fl l
 and
 .Fl t
@@ -68,26 +70,68 @@ on the file system is less than
 The following options are available:
 .Bl -tag -width Ds
 .It Fl a
-Show all mount points,
+If no
+.Ar file ,
+or
+.Ar file_system
+arguments are givem, show all mount points,
 including those that were mounted with the
 .Dv MNT_IGNORE
 flag.
+Note that for file systems specified on the command
+line, that mount option is never considered.
+.It Fl b
+Show space as units of basic blocks (512 bytes).
+This is normally the default; this option can be used to
+override a conflicting setting in the environment variable
+.Ev BLOCKSIZE .
 .It Fl c
 Display a grand total for all shown mount points.
+When combined with
+.Fl f
+only the total for the mount points which otherwise
+would be included is shown, not the individual entries.
+.It Fl f
+Display only the available free space (or with
+.Fl i ,
+free inodes) in a minimal format.
+When there is to be only one line of output, only the value
+is shown, otherwise the value and the mount point,
+separated by a single space, are printed.
+For free space, the
+.Fl b ,
+.Fl g ,
+.Fl H ,
+.Fl h ,
+.Fl k
+and
+.Fl m
+options, and
+.Ev BLOCKSIZE
+are all used as normal.
+This option implies
+.Fl N
+and is incompatible with
+.Fl P
+and
+.Fl G .
 .It Fl G
 Display all the fields of the structure(s) returned by
 .Xr statvfs 2 .
 This option cannot be used with the
+.Fl f ,
 .Fl i
 or
 .Fl P
-options, and it is modelled after the Solaris
+options, and is modelled after the Solaris
 .Fl g
 option.
 This option will override the
+.Fl b ,
 .Fl g ,
+.Fl H ,
 .Fl h ,
-.Fl k ,
+.Fl k
 and
 .Fl m
 options, as well as any setting of
@@ -95,20 +139,32 @@ options, as well as any setting of
 .It Fl g
 The
 .Fl g
-option causes the numbers to be reported in gigabytes (1024*1024*1024
+option causes size numbers to be reported in gigabytes (1024*1024*1024
 bytes).
 .It Fl h
-"Human-readable" output.
+Use
+.Dq human-readable
+output for space data.
 Use unit suffixes: Byte, Kilobyte, Megabyte,
 Gigabyte, Terabyte, Petabyte, Exabyte in order to reduce the number of
 digits to four or less.
+.It Fl H
+As with
+.Fl h
+but using powers of 10 (1000) rather than 2 (1024).
 .It Fl i
 Include statistics on the number of free inodes.
+When combined with
+.Fl f
+only the number of free inodes is shown.
 .It Fl k
-By default, all sizes are reported in 512-byte block counts.
+By default, all sizes are reported in 512-byte block counts,
+unless the
+.Ev BLOCKSIZE
+environment variable is set.
 The
 .Fl k
-option causes the numbers to be reported in kilobytes (1024 bytes).
+option causes the size numbers to be reported in kilobytes (1024 bytes).
 .It Fl l
 Display statistics only about mounted file systems with the
 .Dv MNT_LOCAL
@@ -118,7 +174,16 @@ warning is issued and no information is 
 .It Fl m
 The
 .Fl m
-option causes the numbers to be reported in megabytes (1024*1024 bytes).
+option causes size numbers to be reported in megabytes (1024*1024 bytes).
+.It Fl N
+Suppress the header line normally output.
+This option is ignored with
+.Fl G
+which has no header line to ignore,
+and with
+.Fl P
+which requires the header line to maintain
+the portable format it is designed to emulate.
 .It Fl n
 Print out the previously obtained statistics from the file systems.
 This option should be used if it is possible that one or more
@@ -131,22 +196,7 @@ with the possibly stale statistics that 
 .It Fl P
 Produce output in the following portable format:
 .Pp
-If both the
-.Fl P
-and
-.Fl k
-option are specified, the output will be preceded by the following header
-line, formatted to match the data following it:
-.Bd -literal
-"Filesystem 1024-blocks Used Available Capacity Mounted on\en"
-.Ed
-.Pp
-If the
-.Fl P
-option is specified without the
-.Fl k
-options, the output will be preceded by the following header line,
-formatted to match the data following it:
+The output will be preceded by the following header line:
 .Bd -literal
 "Filesystem <blksize>-blocks Used Available Capacity Mounted on\en"
 .Ed
@@ -161,7 +211,10 @@ The header line is followed by data form
 Note that the
 .Fl i
 option may not be specified with
-.Fl P .
+.Fl P ,
+and the
+.Ar blksize
+is required to be 512 or 1024.
 .It Fl t Ar type
 Is used to indicate the actions should only be taken on
 file systems of the specified type.
@@ -185,19 +238,31 @@ file systems, the
 .Fl W
 option is silently ignored for those file systems.
 .El
+.Pp
+If more than one of
+.Fl b ,
+.Fl g ,
+.Fl H ,
+.Fl h ,
+.Fl k
+or
+.FL m
+is given, the last of those specified is used.
 .Sh ENVIRONMENT
 .Bl -tag -width BLOCKSIZE
 .It Ev BLOCKSIZE
 If the environment variable
 .Ev BLOCKSIZE
-is set, and the
+is set, and none of the
+.Fl b ,
 .Fl g ,
+.Fl H ,
 .Fl h ,
 .Fl k
 and
 .Fl m
-options are not specified, the block counts will be displayed in units of that
-size block.
+options are specified,
+the block counts will be displayed in units of that size block.
 .El
 .Sh SEE ALSO
 .Xr quota 1 ,
@@ -206,6 +271,7 @@ size block.
 .Xr statvfs 2 ,
 .Xr getbsize 3 ,
 .Xr getmntinfo 3 ,
+.Xr humanize_number 3 ,
 .Xr fs 5 ,
 .Xr fstab 5 ,
 .Xr mount 8 ,
@@ -216,3 +282,7 @@ A
 .Nm
 utility appeared in
 .At v1 .
+The
+.Fl f
+option was added in
+.Nx 10 .

Index: src/bin/df/df.c
diff -u src/bin/df/df.c:1.99 src/bin/df/df.c:1.100
--- src/bin/df/df.c:1.99	Mon Nov 29 05:59:58 2021
+++ src/bin/df/df.c	Mon Aug  8 16:50:35 2022
@@ -1,4 +1,4 @@
-/*	$NetBSD: df.c,v 1.99 2021/11/29 05:59:58 simonb Exp $ */
+/*	$NetBSD: df.c,v 1.100 2022/08/08 16:50:35 kre Exp $ */
 
 /*
  * Copyright (c) 1980, 1990, 1993, 1994
@@ -45,7 +45,7 @@ __COPYRIGHT(
 #if 0
 static char sccsid[] = "@(#)df.c	8.7 (Berkeley) 4/2/94";
 #else
-__RCSID("$NetBSD: df.c,v 1.99 2021/11/29 05:59:58 simonb Exp $");
+__RCSID("$NetBSD: df.c,v 1.100 2022/08/08 16:50:35 kre Exp $");
 #endif
 #endif /* not lint */
 
@@ -76,34 +76,45 @@ __dead static void usage(void);
 static void	 prthumanval(int64_t, int);
 static void	 prthuman(const struct statvfs *, int64_t, int64_t);
 
-static int	 aflag, cflag, gflag, hflag, iflag, lflag, nflag, Pflag, Wflag;
+static int	 aflag, cflag, fflag, gflag, hflag, iflag, lflag;
+static int	 Nflag, nflag, Pflag, Wflag;
 static long	 usize;
 static char	**typelist;
+static size_t	 mntcount;
 
 #define WIDTH_INODE	10
 #define WIDTH_BLKSIZE	12
 static int blksize_width = WIDTH_BLKSIZE;
 
+static int fudgeunits = 0;
+
 int
 main(int argc, char *argv[])
 {
 	struct stat stbuf;
 	struct statvfs *mntbuf, totals;
 	int ch, maxwidth, width;
-	size_t i, mntcount;
+	size_t i;
 	char *mntpt;
 
 	setprogname(argv[0]);
 	(void)setlocale(LC_ALL, "");
 
-	while ((ch = getopt(argc, argv, "acGghiklmnPt:W")) != -1)
+	while ((ch = getopt(argc, argv, "abcfGgHhiklmNnPt:W")) != -1)
 		switch (ch) {
 		case 'a':
 			aflag = 1;
 			break;
+		case 'b':
+			hflag = 0;
+			usize = 512;
+			break;
 		case 'c':
 			cflag = 1;
 			break;
+		case 'f':
+			fflag = 1;
+			break;
 		case 'g':
 			hflag = 0;
 			usize = 1024 * 1024 * 1024;
@@ -111,6 +122,9 @@ main(int argc, char *argv[])
 		case 'G':
 			gflag = 1;
 			break;
+		case 'H':
+			fudgeunits = HN_DIVISOR_1000;
+			/* FALL THROUGH */
 		case 'h':
 			hflag = 1;
 			usize = 0;
@@ -129,6 +143,9 @@ main(int argc, char *argv[])
 			hflag = 0;
 			usize = 1024 * 1024;
 			break;
+		case 'N':
+			Nflag = 1;
+			break;
 		case 'n':
 			nflag = 1;
 			break;
@@ -149,12 +166,18 @@ main(int argc, char *argv[])
 			usage();
 		}
 
+	if (fflag && (Pflag || gflag))
+		errx(EXIT_FAILURE,
+		    "only one of -f -G and -P may be specified");
 	if (gflag && (Pflag || iflag))
 		errx(EXIT_FAILURE,
 		    "only one of -G and -P or -i may be specified");
 	if (Pflag && iflag)
 		errx(EXIT_FAILURE,
 		    "only one of -P and -i may be specified");
+	if (fflag)
+		Nflag = 1;
+
 #if 0
 	/*
 	 * The block size cannot be checked until after getbsize() is called.
@@ -227,9 +250,12 @@ main(int argc, char *argv[])
 		if (cflag)
 			addstat(&totals, &mntbuf[i]);
 	}
-	for (i = 0; i < mntcount; i++)
-		prtstat(&mntbuf[i], maxwidth);
 
+	if (cflag == 0 || fflag == 0)
+		for (i = 0; i < mntcount; i++)
+			prtstat(&mntbuf[i], maxwidth);
+
+	mntcount = fflag;
 	if (cflag)
 		prtstat(&totals, maxwidth);
 
@@ -239,13 +265,13 @@ main(int argc, char *argv[])
 static char *
 getmntpt(const char *name)
 {
-	size_t mntcount, i;
+	size_t count, i;
 	struct statvfs *mntbuf;
 
-	mntcount = getmntinfo(&mntbuf, MNT_NOWAIT);
-	if (mntcount == 0)
+	count = getmntinfo(&mntbuf, MNT_NOWAIT);
+	if (count == 0)
 		err(EXIT_FAILURE, "Can't get mount information");
-	for (i = 0; i < mntcount; i++) {
+	for (i = 0; i < count; i++) {
 		if (!strcmp(mntbuf[i].f_mntfromname, name))
 			return mntbuf[i].f_mntonname;
 	}
@@ -312,17 +338,17 @@ maketypelist(char *fslist)
  * current (not cached) info.  Returns the new count of valid statvfs bufs.
  */
 static size_t
-regetmntinfo(struct statvfs **mntbufp, size_t mntcount)
+regetmntinfo(struct statvfs **mntbufp, size_t count)
 {
 	size_t i, j;
 	struct statvfs *mntbuf;
 
 	if (!lflag && typelist == NULL && aflag)
-		return nflag ? mntcount : (size_t)getmntinfo(mntbufp, MNT_WAIT);
+		return nflag ? count : (size_t)getmntinfo(mntbufp, MNT_WAIT);
 
 	mntbuf = *mntbufp;
 	j = 0;
-	for (i = 0; i < mntcount; i++) {
+	for (i = 0; i < count; i++) {
 		if (!aflag && (mntbuf[i].f_flag & MNT_IGNORE) != 0)
 			continue;
 		if (lflag && (mntbuf[i].f_flag & MNT_LOCAL) == 0)
@@ -355,7 +381,7 @@ prthumanval(int64_t bytes, int width)
 
 	(void)humanize_number(buf, sizeof(buf) - (bytes < 0 ? 0 : 1),
 	    bytes, "", HN_AUTOSCALE,
-	    HN_B | HN_NOSPACE | HN_DECIMAL);
+	    HN_B | HN_NOSPACE | HN_DECIMAL | fudgeunits);
 
 	(void)printf("%*s", width, buf);
 }
@@ -465,6 +491,10 @@ prtstat(const struct statvfs *sfsp, int 
 		maxwidth = 12;
 	if (++timesthrough == 1) {
 		switch (blocksize = usize) {
+		case 512:
+			header = "512-blocks";
+			headerlen = (int)strlen(header);
+			break;
 		case 1024:
 			header = Pflag ? "1024-blocks" : "1K-blocks";
 			headerlen = (int)strlen(header);
@@ -506,7 +536,7 @@ prtstat(const struct statvfs *sfsp, int 
 				    "non-standard block size incompatible with -P");
 			(void)printf("Filesystem %s Used Available Capacity "
 			    "Mounted on\n", header);
-		} else {
+		} else if (!Nflag) {
 			(void)printf("%-*.*s %*s %*s %*s %%Cap",
 			    maxwidth, maxwidth, "Filesystem",
 			    blksize_width, header,
@@ -547,6 +577,22 @@ prtstat(const struct statvfs *sfsp, int 
 		return;
 	}
 
+	if (fflag) {
+		if (iflag)
+			(void)printf("%jd", sfsp->f_ffree);
+		else if (hflag)
+			prthumanval(bavail * sfsp->f_frsize, 1);
+		else
+			(void)printf("%jd", fsbtoblk(bavail,
+			    sfsp->f_frsize, blocksize));
+
+		if (mntcount != 1)
+			(void)printf(" %s\n", sfsp->f_mntonname);
+		else
+			(void)printf("\n");
+		return;
+	}
+
 	(void)printf("%-*.*s ", maxwidth, maxwidth, mntfromname);
 
 	if (hflag)
@@ -577,8 +623,8 @@ usage(void)
 {
 
 	(void)fprintf(stderr,
-	    "Usage: %s [-aglnW] [-Ghkm|-ihkm|-Pk] [-t type] [file | "
-	    "file_system ...]\n",
+	    "Usage: %s [-alnW] [-G|-Pbk|-bfgHhikm] [-t type] [file | "
+	    "file_system]...\n",
 	    getprogname());
 	exit(1);
 	/* NOTREACHED */

Reply via email to