[4446] in Athena Bugs
fixes for /bin/df
daemon@ATHENA.MIT.EDU (John Carr)
Wed Mar 7 19:55:03 1990
To: bugs@ATHENA.MIT.EDU
Date: Wed, 07 Mar 90 19:54:30 EST
From: John Carr <jfc@ATHENA.MIT.EDU>
Replace my previous message about df with this one. This fixes a
couple problems I found after I mailed that message. If also contains
patches to df and the kernel to handle nfs filesystems better with the
"-i" flag (the kernel returns 0 files, and df notes this and prints
"???").
[This fixes changes.70 notes 42 & 53.]
Apply this patch to sys/nfs/nfs_vfsops.c:
*** /tmp/,RCSt1000293 Wed Mar 7 19:45:36 1990
--- nfs_vfsops.c Wed Mar 7 19:17:34 1990
***************
*** 305,310 ****
--- 305,311 ----
} else {
mi->mi_stsize = fs.fs_tsize;
}
+ bzero(sbp, sizeof(*sbp));
sbp->f_bsize = fs.fs_bsize;
sbp->f_blocks = fs.fs_blocks;
sbp->f_bfree = fs.fs_bfree;
Apply this patch to /source/bsd-43/common/bin/df.c:
*** /source/bsd-4.3/common/bin/df.c Wed Apr 13 14:08:41 1988
--- df.c Wed Mar 7 19:47:21 1990
***************
*** 15,21 ****
#include <mntent.h>
char *mpath();
! int iflag;
int type;
char *typestr;
--- 15,21 ----
#include <mntent.h>
char *mpath();
! int iflag, fflag;
int type;
char *typestr;
***************
*** 32,40 ****
int argc;
char **argv;
{
! int i;
struct stat statb;
- char tmpname[1024];
while (argc > 1 && argv[1][0]=='-') {
switch (argv[1][1]) {
--- 32,39 ----
int argc;
char **argv;
{
! int i, estat = 1;
struct stat statb;
while (argc > 1 && argv[1][0]=='-') {
switch (argv[1][1]) {
***************
*** 50,55 ****
--- 49,58 ----
argc--;
break;
+ case 'f':
+ fflag++;
+ break;
+
default:
usage();
}
***************
*** 74,121 ****
}
while (mnt = getmntent(mtabp)) {
if (strcmp(mnt->mnt_type, MNTTYPE_IGNORE) == 0 ||
! strcmp(mnt->mnt_type, MNTTYPE_SWAP) == 0)
continue;
! if (!strcmp(mnt->mnt_type, MNTTYPE_NFS) && iflag)
! continue;
! if (type && strcmp(typestr, mnt->mnt_type)) {
! continue;
! }
! if ((stat(mnt->mnt_fsname, &statb) >= 0) &&
! (((statb.st_mode & S_IFBLK) == S_IFBLK) ||
! ((statb.st_mode & S_IFCHR) == S_IFCHR))) {
! strcpy(tmpname, mnt->mnt_fsname);
! dfreedev(tmpname);
! } else {
! dfreemnt(mnt->mnt_dir, mnt);
! }
}
endmntent(mtabp);
! exit(0);
}
for (i=1; i<argc; i++) {
struct mntent *mnt;
! if (stat(argv[i], &statb) < 0) {
! perror(argv[i]);
} else {
! if ((statb.st_mode & S_IFBLK) == S_IFBLK ||
! (statb.st_mode & S_IFCHR) == S_IFCHR) {
! dfreedev(argv[i]);
! } else {
! if ((mnt = getmntpt(argv[i])) != NULL)
! if (type &&
! strcmp(typestr, mnt->mnt_type)) {
! continue;
! }
! dfreemnt(argv[i], mnt);
! }
}
}
! exit(0);
}
! dfreedev(file)
char *file;
{
long totalblks, availblks, avail, free, used;
--- 77,118 ----
}
while (mnt = getmntent(mtabp)) {
if (strcmp(mnt->mnt_type, MNTTYPE_IGNORE) == 0 ||
! strcmp(mnt->mnt_type, MNTTYPE_SWAP) == 0 ||
! iflag && strcmp(mnt->mnt_type, MNTTYPE_NFS) == 0)
continue;
! if(type && strcmp(mnt->mnt_type, typestr))
! continue;
! if(dfreemnt(mnt->mnt_dir, mnt) == 0)
! estat = 0;
}
endmntent(mtabp);
! exit(estat);
}
for (i=1; i<argc; i++) {
struct mntent *mnt;
! if(fflag) {
! if (stat(argv[i], &statb) < 0)
! perror(argv[i]);
! else
! if ((statb.st_mode & S_IFBLK) == S_IFBLK ||
! (statb.st_mode & S_IFCHR) == S_IFCHR)
! dfreedev(argv[i]) || (estat = 0);
! else
! fprintf(stderr,
! "df: %s: Not a block or character special device\n",
! argv[i]);
} else {
! if((mnt = getmntpt(argv[i])) == NULL)
! continue; /* getmntpt prints a message */
! dfreemnt(argv[i], mnt);
! estat = 0;
}
}
! exit(estat);
}
! int dfreedev(file)
char *file;
{
long totalblks, availblks, avail, free, used;
***************
*** 124,134 ****
fi = open(file, 0);
if (fi < 0) {
perror(file);
! return;
}
if (bread(fi, SBLOCK, (char *)&sblock, SBSIZE) == 0) {
(void) close(fi);
! return;
}
printf("%-20.20s", file);
if (iflag) {
--- 121,131 ----
fi = open(file, 0);
if (fi < 0) {
perror(file);
! return 1;
}
if (bread(fi, SBLOCK, (char *)&sblock, SBSIZE) == 0) {
(void) close(fi);
! return 1;
}
printf("%-20.20s", file);
if (iflag) {
***************
*** 153,161 ****
}
printf(" %s\n", mpath(file));
(void) close(fi);
}
! dfreemnt(file, mnt)
char *file;
struct mntent *mnt;
{
--- 150,159 ----
}
printf(" %s\n", mpath(file));
(void) close(fi);
+ return 0;
}
! int dfreemnt(file, mnt)
char *file;
struct mntent *mnt;
{
***************
*** 163,169 ****
if (statfs(file, &fs) < 0) {
perror(file);
! return;
}
if (strlen(mnt->mnt_fsname) > 20) {
--- 161,167 ----
if (statfs(file, &fs) < 0) {
perror(file);
! return 1;
}
if (strlen(mnt->mnt_fsname) > 20) {
***************
*** 177,184 ****
files = fs.f_files;
used = files - fs.f_ffree;
! printf("%8ld%8ld%6.0f%% ", used, fs.f_ffree,
! files == 0? 0.0: (double)used / (double)files * 100.0);
} else {
long totalblks, avail, free, used, reserved;
--- 175,186 ----
files = fs.f_files;
used = files - fs.f_ffree;
! if(files == 0)
! printf(" ??? ??? ??? ");
! else
! printf("%8ld%8ld%6.0f%% ", used, fs.f_ffree,
! files == 0 ? 0.0 :
! (double)used / (double)files * 100.0);
} else {
long totalblks, avail, free, used, reserved;
***************
*** 197,202 ****
--- 199,205 ----
printf(" ");
}
printf(" %s\n", mnt->mnt_dir);
+ return 0;
}
/*
***************
*** 216,221 ****
--- 219,229 ----
return(NULL);
}
+ /* Since it is faster to scan mtab than to stat a file
+ on average (consdering the chance of contacting a hung
+ remote file server), scan all of mtab first to find the mount
+ point */
+
if ((mntp = setmntent(MOUNTED, "r")) == 0) {
perror(MOUNTED);
exit(1);
***************
*** 223,228 ****
--- 231,250 ----
mntsave = NULL;
while ((mnt = getmntent(mntp)) != 0) {
+ if(strcmp(mnt->mnt_dir, file))
+ continue;
+ mntsave = mntdup(mnt);
+ endmntent(mntp);
+ return mntsave;
+ }
+ endmntent(mntp);
+
+ if ((mntp = setmntent(MOUNTED, "r")) == 0) {
+ perror(MOUNTED);
+ exit(1);
+ }
+
+ while ((mnt = getmntent(mntp)) != 0) {
if (strcmp(mnt->mnt_type, MNTTYPE_IGNORE) == 0 ||
strcmp(mnt->mnt_type, MNTTYPE_SWAP) == 0)
continue;
***************
*** 229,234 ****
--- 251,257 ----
if ((stat(mnt->mnt_dir, &dirstat) >= 0) &&
(filestat.st_dev == dirstat.st_dev)) {
mntsave = mntdup(mnt);
+ break;
}
}
endmntent(mntp);
***************
*** 236,242 ****
return(mntsave);
} else {
fprintf(stderr, "Couldn't find mount point for %s\n", file);
! exit(1);
}
/*NOTREACHED*/
}
--- 259,265 ----
return(mntsave);
} else {
fprintf(stderr, "Couldn't find mount point for %s\n", file);
! return NULL;
}
/*NOTREACHED*/
}
Apply this patch to /source/bsd-43/common/man/man1/df.1:
*** /source/bsd-4.3/common/man/man1/df.1 Fri Nov 17 01:35:09 1989
--- df.1 Wed Mar 7 17:47:21 1990
***************
*** 13,30 ****
[
.B \-i
] [
.B \-t
! mount-type ] [ filesystem ... ] [ file ... ]
.SH DESCRIPTION
.I Df
prints out the amount of free disk space
available on the specified
! .I filesystem,
! e.g. ``/dev/rp0a'',
! or on the filesystem in which the specified
.I file,
e.g. ``$HOME'',
! is contained.
If no file system is specified,
the free space on all of
the normally mounted file systems
--- 13,38 ----
[
.B \-i
] [
+ .B \-f
+ ] [
.B \-t
! mount-type ] [ file ... ]
.SH DESCRIPTION
.I Df
prints out the amount of free disk space
available on the specified
! .I filesystem.
! If the
! .B \-f
! flag is used,
! .I file
! can be a special device, e.g. ``/dev/ra0a''.
! If
! .B \-f
! is not used, the filesystem containing
.I file,
e.g. ``$HOME'',
! is used.
If no file system is specified,
the free space on all of
the normally mounted file systems