Subject: bin/32788: fstat(1) doesn't know tmpfs
To: None <gnats-admin@netbsd.org, netbsd-bugs@netbsd.org>
From: KAMADA Ken'ichi <kamada@nanohz.org>
List: netbsd-bugs
Date: 02/10/2006 10:50:00
>Number:         32788
>Category:       bin
>Synopsis:       fstat(1) doesn't know tmpfs
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    bin-bug-people
>State:          open
>Class:          change-request
>Submitter-Id:   net
>Arrival-Date:   Fri Feb 10 10:50:00 +0000 2006
>Originator:     KAMADA Ken'ichi
>Release:        NetBSD 3.99.15
>Organization:
>Environment:
System: NetBSD mitana.nanohz.org 3.99.15 NetBSD 3.99.15 (MITANA) #87: Mon Feb 6 08:55:16 JST 2006 ken@mitana.nanohz.org:/usr/src/sys/arch/i386/compile/MITANA i386
Architecture: i386
Machine: i386
>Description:
fstat(1) doesn't understand tmpfs and shows lines like this:
ken      zsh         3045   wd -         -       ?(19)    -

>How-To-Repeat:
1. mount tmpfs.
2. cd there.
3. fstat and check if the mount point is listed.

>Fix:
Patch attached.
tmpfs.h requires a lot of kernel internal structures, so
the "#define"s around the include files are needed but not nice...

Index: Makefile
===================================================================
RCS file: /cvsroot/src/usr.bin/fstat/Makefile,v
retrieving revision 1.18
diff -u -r1.18 Makefile
--- Makefile	17 Jul 2005 07:36:26 -0000	1.18
+++ Makefile	10 Feb 2006 10:10:34 -0000
@@ -5,7 +5,7 @@
 
 WARNS=	3
 PROG=	fstat
-SRCS=	fstat.c isofs.c ntfs.c ptyfs.c
+SRCS=	fstat.c isofs.c ntfs.c ptyfs.c tmpfs.c
 DPADD=	${LIBKVM}
 LDADD=	-lkvm
 BINGRP=	kmem
Index: fstat.c
===================================================================
RCS file: /cvsroot/src/usr.bin/fstat/fstat.c,v
retrieving revision 1.72
diff -u -r1.72 fstat.c
--- fstat.c	17 Jul 2005 07:36:26 -0000	1.72
+++ fstat.c	10 Feb 2006 10:10:35 -0000
@@ -440,6 +440,10 @@
 			if (!ptyfs_filestat(vp, fsp))
 				badtype = "error";
 			break;
+		case VT_TMPFS:
+			if (!tmpfs_filestat(vp, fsp))
+				badtype = "error";
+			break;
 		case VT_NULL:
 		case VT_OVERLAY:
 		case VT_UMAP:
Index: fstat.h
===================================================================
RCS file: /cvsroot/src/usr.bin/fstat/fstat.h,v
retrieving revision 1.6
diff -u -r1.6 fstat.h
--- fstat.h	17 Jul 2005 07:36:26 -0000	1.6
+++ fstat.h	10 Feb 2006 10:10:35 -0000
@@ -52,3 +52,4 @@
 int	isofs_filestat(struct vnode *, struct filestat *);
 int	ntfs_filestat(struct vnode *, struct filestat *);
 int	ptyfs_filestat(struct vnode *, struct filestat *);
+int	tmpfs_filestat(struct vnode *, struct filestat *);
Index: tmpfs.c
===================================================================
RCS file: tmpfs.c
diff -N tmpfs.c
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ tmpfs.c	10 Feb 2006 10:10:35 -0000
@@ -0,0 +1,97 @@
+/*	$NetBSD$	*/
+
+/*-
+ * Copyright (c) 2006 The NetBSD Foundation, Inc.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *	This product includes software developed by the NetBSD
+ *	Foundation, Inc. and its contributors.
+ * 4. Neither the name of The NetBSD Foundation nor the names of its
+ *    contributors may be used to endorse or promote products derived
+ *    from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
+ * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <sys/cdefs.h>
+__RCSID("$NetBSD$");
+
+#define _KERNEL				/* To expose boolean_t */
+#include <sys/types.h>
+#undef _KERNEL
+#include <sys/param.h>
+#include <sys/time.h>
+#include <sys/proc.h>
+#include <sys/user.h>
+#include <sys/stat.h>
+#define _KERNEL				/* To expose struct pool */
+#include <sys/pool.h>
+#undef _KERNEL
+#include <sys/vnode.h>
+#include <sys/mount.h>
+#include <machine/vmparam.h>		/* For PAGE_SIZE */
+
+struct componentname;
+#define KASSERT(exp) assert(exp)
+#include <assert.h>
+#define _KERNEL
+#include <fs/tmpfs/tmpfs.h>
+#undef _KERNEL
+
+#include <err.h>
+#include <kvm.h>
+#include "fstat.h"
+
+int
+tmpfs_filestat(struct vnode *vp, struct filestat *fsp)
+{
+	struct tmpfs_node tn;
+	struct mount mt;
+
+	if (!KVM_READ(VP_TO_TMPFS_NODE(vp), &tn, sizeof(tn))) {
+		dprintf("can't read tmpfs_node at %p for pid %d",
+		    VP_TO_TMPFS_NODE(vp), Pid);
+		return 0;
+	}
+	if (!KVM_READ(vp->v_mount, &mt, sizeof(mt))) {
+		dprintf("can't read mount at %p for pid %d",
+		    vp->v_mount, Pid);
+		return 0;
+	}
+
+	fsp->fsid = mt.mnt_stat.f_fsidx.__fsid_val[0];
+	fsp->fileid = (long)tn.tn_id;
+	fsp->mode = tn.tn_mode | getftype(vp->v_type);
+	fsp->size = tn.tn_size;
+	switch (tn.tn_type) {
+	case VBLK:
+	case VCHR:
+		fsp->rdev = tn.tn_rdev;
+		break;
+	default:
+		fsp->rdev = 0;
+		break;
+	}
+
+	return 1;
+}