PERFORCE change 109953 for review

Todd Miller millert at FreeBSD.org
Tue Nov 14 18:39:36 UTC 2006


http://perforce.freebsd.org/chv.cgi?CH=109953

Change 109953 by millert at millert_g5tower on 2006/11/14 18:38:53

	Move mmap checks from vnode to file.
	Add file_has_perm to sebsd.c that checks both the fd label and
	the underlying vnode label, similar to what SELinux does.

Affected files ...

.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/bsd/kern/kern_mman.c#4 edit
.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_file.c#5 edit
.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_framework.h#12 edit
.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_policy.h#20 edit
.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_vfs.c#15 edit
.. //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/sorted-policynames.vim#2 edit
.. //depot/projects/trustedbsd/sedarwin8/policies/color/mac_color.c#10 edit
.. //depot/projects/trustedbsd/sedarwin8/policies/mls/mac_mls.c#18 edit
.. //depot/projects/trustedbsd/sedarwin8/policies/readonly/mac_readonly.c#7 edit
.. //depot/projects/trustedbsd/sedarwin8/policies/sedarwin/sedarwin/sebsd.c#34 edit
.. //depot/projects/trustedbsd/sedarwin8/policies/vanity/vanity.c#7 edit

Differences ...

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/bsd/kern/kern_mman.c#4 (text+ko) ====

@@ -373,8 +373,8 @@
 
 			handle = (void *)vp;
 #ifdef MAC
-			error = mac_vnode_check_mmap(vfs_context_ucred(&context),
-			    vp, prot, flags, &maxprot);
+			error = mac_file_check_mmap(vfs_context_ucred(&context),
+			    fp->f_fglob, prot, flags, &maxprot);
 			if (error) {
 				(void)vnode_put(vp);
 				goto bad;

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_file.c#5 (text+ko) ====

@@ -221,3 +221,39 @@
 	MAC_CHECK(file_check_set, cred, fg, buf, buflen);
 	return (error);
 }
+
+/*
+ * On some platforms, VM_PROT_READ implies VM_PROT_EXECUTE. If that is true,
+ * both prot and maxprot will have VM_PROT_EXECUTE set after file_check_mmap
+ * if VM_PROT_READ is set.
+ *
+ * The type of maxprot in file_check_mmap must be equivalent to vm_prot_t *
+ * (defined in <mach/vm_prot.h>). mac_policy.h does not include any header
+ * files, so cannot use the typedef itself.
+ */
+int
+mac_file_check_mmap(struct ucred *cred, struct fileglob *fg, int prot,
+    int flags, int *maxprot)
+{
+	int error;
+	int maxp;
+
+	maxp = *maxprot;
+	MAC_CHECK(file_check_mmap, cred, fg, fg->fg_label, prot, flags, &maxp);
+	if ((maxp | *maxprot) != *maxprot)
+		panic("file_check_mmap increased max protections");
+	*maxprot = maxp;
+	return (error);
+}
+
+void
+mac_file_check_mmap_downgrade(struct ucred *cred, struct fileglob *fg,
+    int *prot)
+{
+	int result = *prot;
+
+	MAC_PERFORM(file_check_mmap_downgrade, cred, fg, fg->fg_label,
+	    &result);
+
+	*prot = result;
+}

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_framework.h#12 (text+ko) ====

@@ -310,6 +310,10 @@
 	    struct fileglob *fg, char oldflags, char newflags);
 int	mac_file_check_get_offset(struct ucred *cred, struct fileglob *fg);
 int	mac_file_check_change_offset(struct ucred *cred, struct fileglob *fg);
+int	mac_file_check_mmap(struct ucred *cred, struct fileglob *fg,
+	    int prot, int flags, int *maxprot);
+void	mac_file_check_mmap_downgrade(struct ucred *cred, struct fileglob *fg,
+	    int *prot);
 int	mac_file_check_set(struct ucred *cred, struct fileglob *fg,
 	    char *buf, int buflen);
 int	mac_sysvsem_check_semget(struct ucred *cred,
@@ -407,10 +411,6 @@
 int	mac_vnode_check_listextattr(struct ucred *cred, struct vnode *vp);
 int	mac_vnode_check_lookup(struct ucred *cred, struct vnode *dvp,
 	    struct componentname *cnp);
-int	mac_vnode_check_mmap(struct ucred *cred, struct vnode *vp,
-	    int prot, int flags, int *maxprot);
-void	mac_vnode_check_mmap_downgrade(struct ucred *cred, struct vnode *vp,
-	    int *prot);
 int	mac_vnode_check_mprotect(struct ucred *cred, struct vnode *vp,
 	    int prot);
 int	mac_vnode_check_open(struct ucred *cred, struct vnode *vp,

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_policy.h#20 (text+ko) ====

@@ -3901,6 +3901,51 @@
 );
 
 /**
+  @brief Access control check for mapping a file
+  @param cred Subject credential
+  @param fg fileglob representing file to map
+  @param label Policy label associated with vp
+  @param prot mmap protections; see mmap(2)
+  @param flags Type of mapped object; see mmap(2)
+  @param maxprot Maximum rights
+
+  Determine whether the subject identified by the credential should be
+  allowed to map the file represented by fg with the protections specified
+  in prot.  The maxprot field holds the maximum permissions on the new
+  mapping, a combination of VM_PROT_READ, VM_PROT_WRITE, and VM_PROT_EXECUTE.
+  To avoid overriding prior access control checks, a policy should only
+  remove flags from maxprot.
+
+  @return Return 0 if access is granted, otherwise an appropriate value for
+  errno should be returned. Suggested failure: EACCES for label mismatch or
+  EPERM for lack of privilege.
+*/
+typedef int mpo_file_check_mmap_t(
+	struct ucred *cred,
+	struct fileglob *fg,
+	struct label *label,
+	int prot,
+	int flags,
+	int *maxprot
+);
+
+/**
+  @brief Downgrade the mmap protections
+  @param cred Subject credential
+  @param fg file to map
+  @param label Policy label associated with vp
+  @param prot mmap protections to be downgraded
+
+  Downgrade the mmap protections based on the subject and object labels.
+*/
+typedef void mpo_file_check_mmap_downgrade_t(
+	struct ucred *cred,
+	struct fileglob *fg,
+	struct label *label,
+	int *prot
+);
+
+/**
   @brief Access control for changing the offset of a file descriptor
   @param cred Subject credential
   @param fg Fileglob structure
@@ -4634,51 +4679,6 @@
 );
 
 /**
-  @brief Access control check for mapping the vnode
-  @param cred Subject credential
-  @param vp vnode to map
-  @param label Policy label associated with vp
-  @param prot mmap protections; see mmap(2)
-  @param flags Type of mapped object; see mmap(2)
-  @param maxprot Maximum rights
-
-  Determine whether the subject identified by the credential should be
-  allowed to map the vnode vp with the protections specified in prot.
-  The maxprot field holds the maximum permissions on the new mapping,
-  a combination of VM_PROT_READ, VM_PROT_WRITE, and VM_PROT_EXECUTE.
-  To avoid overriding prior access control checks, a policy should only
-  remove flags from maxprot.
-
-  @return Return 0 if access is granted, otherwise an appropriate value for
-  errno should be returned. Suggested failure: EACCES for label mismatch or
-  EPERM for lack of privilege.
-*/
-typedef int mpo_vnode_check_mmap_t(
-	struct ucred *cred,
-	struct vnode *vp,
-	struct label *label,
-	int prot,
-	int flags,
-	int *maxprot
-);
-
-/**
-  @brief Downgrade the mmap protections
-  @param cred Subject credential
-  @param vp vnode to map
-  @param label Policy label associated with vp
-  @param prot mmap protections to be downgraded
-
-  Downgrade the mmap protections based on the subject and object labels.
-*/
-typedef void mpo_vnode_check_mmap_downgrade_t(
-	struct ucred *cred,
-	struct vnode *vp,
-	struct label *label,
-	int *prot
-);
-
-/**
   @brief Access control check for setting memory protections
   @param cred Subject credential
   @param vp Mapped vnode
@@ -5529,10 +5529,12 @@
 	mpo_file_check_get_flags_t		*mpo_file_check_get_flags;
 	mpo_file_check_get_offset_t		*mpo_file_check_get_offset;
 	mpo_file_check_get_ofileflags_t		*mpo_file_check_get_ofileflags;
+	mpo_file_check_get_t			*mpo_file_check_get;
 	mpo_file_check_inherit_t		*mpo_file_check_inherit;
 	mpo_file_check_ioctl_t			*mpo_file_check_ioctl;
+	mpo_file_check_mmap_downgrade_t		*mpo_file_check_mmap_downgrade;
+	mpo_file_check_mmap_t			*mpo_file_check_mmap;
 	mpo_file_check_receive_t		*mpo_file_check_receive;
-	mpo_file_check_get_t			*mpo_file_check_get;
 	mpo_file_check_set_t			*mpo_file_check_set;
 	mpo_port_check_method_t			*mpo_port_check_method;
 	mpo_posixsem_check_create_t		*mpo_posixsem_check_create;
@@ -5613,8 +5615,6 @@
 	mpo_vnode_check_link_t			*mpo_vnode_check_link;
 	mpo_vnode_check_listextattr_t		*mpo_vnode_check_listextattr;
 	mpo_vnode_check_lookup_t		*mpo_vnode_check_lookup;
-	mpo_vnode_check_mmap_t			*mpo_vnode_check_mmap;
-	mpo_vnode_check_mmap_downgrade_t	*mpo_vnode_check_mmap_downgrade;
 	mpo_vnode_check_mprotect_t		*mpo_vnode_check_mprotect;
 	mpo_vnode_check_open_t			*mpo_vnode_check_open;
 	mpo_vnode_check_read_t			*mpo_vnode_check_read;

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/mac_vfs.c#15 (text+ko) ====

@@ -513,42 +513,6 @@
 	return (error);
 }
 
-/*
- * On some platforms, VM_PROT_READ implies VM_PROT_EXECUTE. If that is true,
- * both prot and maxprot will have VM_PROT_EXECUTE set after vnode_check_mmap
- * if VM_PROT_READ is set.
- *
- * The type of maxprot in vnode_check_mmap must be equivalent to vm_prot_t *
- * (defined in <mach/vm_prot.h>). mac_policy.h does not include any header files,
- * so cannot use the typedef itself.
- */
-
-int
-mac_vnode_check_mmap(struct ucred *cred, struct vnode *vp, int prot, int flags,
-    int *maxprot)
-{
-	int error;
-	int maxp;
-
-	maxp = *maxprot;
-	MAC_CHECK(vnode_check_mmap, cred, vp, vp->v_label, prot, flags, &maxp);
-	if ((maxp | *maxprot) != *maxprot)
-		panic("vnode_check_mmap increased max protections");
-	*maxprot = maxp;
-	return (error);
-}
-
-void
-mac_vnode_check_mmap_downgrade(struct ucred *cred, struct vnode *vp, int *prot)
-{
-	int result = *prot;
-
-	MAC_PERFORM(vnode_check_mmap_downgrade, cred, vp, vp->v_label,
-	    &result);
-
-	*prot = result;
-}
-
 int
 mac_vnode_check_mprotect(struct ucred *cred, struct vnode *vp, int prot)
 {

==== //depot/projects/trustedbsd/sedarwin8/darwin/xnu/security/sorted-policynames.vim#2 (text+ko) ====

@@ -25,6 +25,8 @@
 typedef mpo_devfs_label_update_t(
 typedef mpo_file_check_fcntl_t(
 typedef mpo_file_check_get_t(
+typedef mpo_file_check_mmap_downgrade_t(
+typedef mpo_file_check_mmap_t(
 typedef mpo_file_check_set_t(
 typedef mpo_iokit_check_device_t(
 typedef mpo_lctx_check_label_update_t(
@@ -210,8 +212,6 @@
 typedef mpo_vnode_check_link_t(
 typedef mpo_vnode_check_listextattr_t(
 typedef mpo_vnode_check_lookup_t(
-typedef mpo_vnode_check_mmap_downgrade_t(
-typedef mpo_vnode_check_mmap_t(
 typedef mpo_vnode_check_mprotect_t(
 typedef mpo_vnode_check_open_t(
 typedef mpo_vnode_check_read_t(

==== //depot/projects/trustedbsd/sedarwin8/policies/color/mac_color.c#10 (text+ko) ====

@@ -502,7 +502,7 @@
 }
 
 static int
-color_vnode_check_mmap(struct ucred *cred, struct vnode *vp,
+color_file_check_mmap(struct ucred *cred, struct fileglob *fg,
     struct label *label, int prot, int flags, int *maxprot) 
 {
 
@@ -510,7 +510,7 @@
 }
 
 static void
-color_vnode_check_mmap_downgrade(struct ucred *cred, struct vnode *vp,
+color_file_check_mmap_downgrade(struct ucred *cred, struct fileglob *fg,
     struct label *label, int *prot) 
 {
 
@@ -701,6 +701,9 @@
 
 	.mpo_cred_check_label_update	= color_cred_check_label_update,
 
+	.mpo_file_check_mmap		= color_file_check_mmap,
+	.mpo_file_check_mmap_downgrade	= color_file_check_mmap_downgrade,
+
 	.mpo_lctx_notify_create		= color_lctx_notify_create,
 	.mpo_lctx_notify_join		= color_lctx_notify_join,
 	.mpo_lctx_notify_leave		= color_lctx_notify_leave,
@@ -721,8 +724,6 @@
 	.mpo_vnode_check_link		= color_vnode_check_link,
 	.mpo_vnode_check_listextattr	= color_vnode_check_listextattr,
 	.mpo_vnode_check_lookup		= color_vnode_check_lookup,
-	.mpo_vnode_check_mmap		= color_vnode_check_mmap,
-	.mpo_vnode_check_mmap_downgrade	= color_vnode_check_mmap_downgrade,
 	.mpo_vnode_check_mprotect	= color_vnode_check_mprotect,
 	.mpo_vnode_check_open		= color_vnode_check_open,
 	.mpo_vnode_check_read		= color_vnode_check_read,

==== //depot/projects/trustedbsd/sedarwin8/policies/mls/mac_mls.c#18 (text+ko) ====

@@ -3444,7 +3444,7 @@
 }
 
 static int
-mac_mls_vnode_check_mmap(struct ucred *cred, struct vnode *vp,
+mac_mls_file_check_mmap(struct ucred *cred, struct fileglob *fg,
     struct label *label, int prot, int flags, int *maxprot)
 {
 	struct mac_mls *subj, *obj;
@@ -3487,13 +3487,13 @@
  * combination of what each policy thinks it should be.
  */
 static void
-mac_mls_vnode_check_mmap_downgrade(struct ucred *cred, struct vnode *vp,
+mac_mls_file_check_mmap_downgrade(struct ucred *cred, struct fileglob *fg,
     struct label *vlabel, int *prot)
 {
 
 	if (!mac_mls_enabled)
 		return;
-#warning Implement mac_mls_vnode_check_mmap_downgrade()
+#warning Implement mac_mls_file_check_mmap_downgrade()
 	return;
 }
 
@@ -4088,8 +4088,8 @@
     .mpo_vnode_check_link               = mac_mls_vnode_check_link,
     .mpo_vnode_check_listextattr        = mac_mls_vnode_check_listextattr,
     .mpo_vnode_check_lookup             = mac_mls_vnode_check_lookup,
-    .mpo_vnode_check_mmap               = mac_mls_vnode_check_mmap,
-    .mpo_vnode_check_mmap_downgrade	= mac_mls_vnode_check_mmap_downgrade,
+    .mpo_file_check_mmap                = mac_mls_file_check_mmap,
+    .mpo_file_check_mmap_downgrade	= mac_mls_file_check_mmap_downgrade,
     .mpo_vnode_check_mprotect		= mac_mls_vnode_check_mprotect,
     .mpo_vnode_check_open               = mac_mls_vnode_check_open,
     .mpo_vnode_check_read               = mac_mls_vnode_check_read,

==== //depot/projects/trustedbsd/sedarwin8/policies/readonly/mac_readonly.c#7 (text+ko) ====

@@ -1,6 +1,8 @@
 #include <sys/types.h>
 #include <sys/conf.h>
 #include <sys/kernel.h>
+#include <sys/file.h>
+#include <sys/file_internal.h>
 #include <sys/malloc.h>
 #include <sys/mman.h>
 #include <sys/mount.h>
@@ -420,11 +422,14 @@
 }
 
 static int
-readonly_vnode_check_mmap(struct ucred *cred, struct vnode *vp,
+readonly_file_check_mmap(struct ucred *cred, struct fileglob *fg,
     struct label *label, int prot, int flags, int *maxprot) 
 {
 
-	return (ro_checkdiraccess(vp, label, (prot & PROT_WRITE) ? FWRITE : FREAD));
+	if (fg->fg_type != DTYPE_VNODE)
+		return (0);
+	return (ro_checkdiraccess((struct vnode *)fg->fg_data, label,
+	    (prot & PROT_WRITE) ? FWRITE : FREAD));
 }
 
 static int
@@ -502,6 +507,7 @@
 	.mpo_policy_destroy		= readonly_policy_destroy,
 	.mpo_policy_init		= readonly_policy_init,
 	.mpo_policy_initbsd		= readonly_policy_initbsd,
+	.mpo_file_check_mmap		= readonly_file_check_mmap,
 	.mpo_vnode_label_init		= readonly_label_init,
 	.mpo_vnode_label_destroy	= readonly_label_destroy,
 	.mpo_vnode_label_recycle	= readonly_label_recycle,
@@ -520,7 +526,6 @@
 	.mpo_vnode_check_deleteextattr	= readonly_vnode_check_deleteextattr,
 	.mpo_vnode_check_exchangedata	= readonly_vnode_check_exchangedata,
 	.mpo_vnode_check_link		= readonly_vnode_check_link,
-	.mpo_vnode_check_mmap		= readonly_vnode_check_mmap,
 	.mpo_vnode_check_open		= readonly_vnode_check_open,
 	.mpo_vnode_check_label_update	= readonly_vnode_check_label_update,
 	.mpo_vnode_check_rename_from	= readonly_vnode_check_rename_from,

==== //depot/projects/trustedbsd/sedarwin8/policies/sedarwin/sedarwin/sebsd.c#34 (text+ko) ====

@@ -467,6 +467,34 @@
 }
 
 static int
+file_has_perm(struct ucred *cred, struct fileglob *fg, struct label *fglabel,
+    u_int32_t perm)
+{
+	struct task_security_struct *tsec;
+	struct file_security_struct *fsec;
+	int rc = 0;
+
+	tsec = SLOT(cred->cr_label);
+	fsec = SLOT(fglabel);
+
+	/* Simple use check if file opened by other sid. */
+	if (tsec->sid != fsec->sid) {
+		rc = avc_has_perm(tsec->sid, fsec->sid, SECCLASS_FD, FD__USE,
+		    NULL);
+		if (rc != 0)
+			return (rc);
+	}
+
+	/* Check underlying vnode if there is one. */
+	if (fg->fg_type == DTYPE_VNODE && fg->fg_data != NULL) {
+		rc = vnode_has_perm(cred, (struct vnode *)fg->fg_data,
+		    NULL, perm);
+	}
+
+	return (rc);
+}
+
+static int
 pipe_has_perm(struct ucred *cred, struct pipe *pipe, u_int32_t perm)
 {
 	struct task_security_struct *task;
@@ -2891,8 +2919,8 @@
 }
 
 static int
-sebsd_vnode_check_mmap(struct ucred *cred, struct vnode *vp,
-    struct label *label, int prot, int flags, int *maxprot)
+sebsd_file_check_mmap(struct ucred *cred, struct fileglob *fg,
+    struct label *fglabel, int prot, int flags, int *maxprot)
 {
 	u_int32_t av;
 
@@ -2900,18 +2928,15 @@
 	 * TBD: Incomplete?
 	 * Write access only matters if the mapping is shared.
 	 */
-	if (vp) {
-		av = FILE__READ;
+	av = FILE__READ;
 
-		if ((prot & PROT_WRITE) && (flags & MAP_SHARED))
-			av |= FILE__WRITE;
+	if ((prot & PROT_WRITE) && (flags & MAP_SHARED))
+		av |= FILE__WRITE;
 
-		if (prot & PROT_EXEC)
-			av |= FILE__EXECUTE;
+	if (prot & PROT_EXEC)
+		av |= FILE__EXECUTE;
 
-		return (vnode_has_perm(cred, vp, NULL, av));
-	}
-	return (0);
+	return (file_has_perm(cred, fg, fglabel, av));
 }
 
 static int
@@ -3653,7 +3678,6 @@
 //	.mpo_vnode_check_kqfilter = sebsd_vnode_check_kqfilter,
 	.mpo_vnode_check_link = sebsd_vnode_check_link,
 	.mpo_vnode_check_lookup = sebsd_vnode_check_lookup,
-	.mpo_vnode_check_mmap = sebsd_vnode_check_mmap,
 	.mpo_vnode_check_mprotect = sebsd_vnode_check_mprotect,
 	.mpo_vnode_check_open = sebsd_vnode_check_open,
 	.mpo_vnode_check_read = sebsd_vnode_check_read,
@@ -3701,6 +3725,7 @@
 	.mpo_file_check_inherit = sebsd_file_check_receive,
 	.mpo_file_check_receive = sebsd_file_check_receive,
 	.mpo_file_check_dup = sebsd_file_check_dup,
+	.mpo_file_check_mmap = sebsd_file_check_mmap,
 
 	/* Mount Points */
 	.mpo_mount_label_init = sebsd_mount_label_init,

==== //depot/projects/trustedbsd/sedarwin8/policies/vanity/vanity.c#7 (text+ko) ====

@@ -4,6 +4,7 @@
 #include <sys/sysctl.h>
 
 #include <sys/proc.h>
+#include <sys/file_internal.h>
 #include <sys/mount_internal.h>
 #include <sys/vnode_internal.h>
 
@@ -315,16 +316,20 @@
 }
 
 static int
-vanity_vnode_check_mmap(struct ucred *cred, struct vnode *vp, struct label *label, int prot, int flags, int *maxprot) 
+vanity_file_check_mmap(struct ucred *cred, struct fileglob *fg,
+    struct label *label, int prot, int flags, int *maxprot) 
 {
-	VANITY(vp);
+	if (fg->fg_type == DTYPE_VNODE)
+		VANITY((struct vnode *)fg->fg_data);
 	return (0);
 }
 
 static void
-vanity_vnode_check_mmap_downgrade(struct ucred *cred, struct vnode *vp, struct label *label, int *prot) 
+vanity_file_check_mmap_downgrade(struct ucred *cred, struct fileglob *fg,
+    struct label *label, int *prot) 
 {
-	VANITY(vp);
+	if (fg->fg_type == DTYPE_VNODE)
+		VANITY((struct vnode *)fg->fg_data);
 }
 
 static int
@@ -473,6 +478,8 @@
 static struct mac_policy_ops mac_vanity_ops = {
 	.mpo_policy_initbsd			= vanity_policy_initbsd,
 
+	.mpo_file_check_mmap		= vanity_file_check_mmap,
+	.mpo_file_check_mmap_downgrade	= vanity_file_check_mmap_downgrade,
 	.mpo_vnode_label_update_extattr	= vanity_vnode_label_update_extattr,
 	.mpo_vnode_label_associate_devfs= vanity_vnode_label_associate_devfs,
 	.mpo_vnode_label_associate_extattr= vanity_vnode_label_associate_extattr,
@@ -501,8 +508,6 @@
 	.mpo_vnode_check_link		= vanity_vnode_check_link,
 	.mpo_vnode_check_listextattr	= vanity_vnode_check_listextattr,
 	.mpo_vnode_check_lookup		= vanity_vnode_check_lookup,
-	.mpo_vnode_check_mmap		= vanity_vnode_check_mmap,
-	.mpo_vnode_check_mmap_downgrade	= vanity_vnode_check_mmap_downgrade,
 	.mpo_vnode_check_mprotect	= vanity_vnode_check_mprotect,
 	.mpo_vnode_check_open		= vanity_vnode_check_open,
 	.mpo_vnode_check_read		= vanity_vnode_check_read,


More information about the trustedbsd-cvs mailing list