Subject: bin/30351: useradd(8) doesn't allow setting permissions of new home [patch]
To: None <gnats-admin@netbsd.org, netbsd-bugs@netbsd.org>
From: Hubert Feyrer <hubert@feyrer.de>
List: netbsd-bugs
Date: 05/27/2005 12:24:00
>Number:         30351
>Category:       bin
>Synopsis:       useradd(8) doesn't allow setting permissions of new home [patch]
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    bin-bug-people
>State:          open
>Class:          change-request
>Submitter-Id:   net
>Arrival-Date:   Fri May 27 12:24:00 +0000 2005
>Originator:     Hubert Feyrer
>Release:        NetBSD ~2.0
>Organization:
bla!
>Environment:
	
	
System: NetBSD miyu 3.0_BETA NetBSD 3.0_BETA (MIYU) #4: Wed May 4 16:16:00 MEST 2005 feyrer@miyu:/home/cvs/src-3/sys/arch/i386/compile/obj.i386/MIYU i386
Architecture: i386
Machine: i386
>Description:
	Someone asked in de.comp.os.unix.bsd if it was possible to create
	home directories with permissions 700, and aparently our useradd(8)
	doesn't support that.

	(Message ID of the posting is <3foefmF8p8rlU1@individual.net>)

>How-To-Repeat:
	RTFM :)
>Fix:
	The following patch adds a -M option to specify permissions. 
	It also implements saving default permissions via "useradd -D".

Index: user.8
===================================================================
RCS file: /cvsroot/src/usr.sbin/user/user.8,v
retrieving revision 1.18
diff -u -r1.18 user.8
--- user.8	5 Feb 2005 15:26:50 -0000	1.18
+++ user.8	27 May 2005 12:22:14 -0000
@@ -31,7 +31,7 @@
 .\" SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 .\"
 .\"
-.Dd January 14, 2004
+.Dd May 27, 2005
 .Dt USER 8
 .Os
 .Sh NAME
@@ -46,10 +46,11 @@
 .Op Fl f Ar inactive-time
 .Op Fl g Ar gid/name/=uid
 .Op Fl L Ar login-class
+.Op Fl M Ar home-perm
 .Op Fl r Ar lowuid..highuid
 .Nm
 .Cm add
-.Op Fl Smov
+.Op Fl moSv
 .Op Fl G Ar secondary-group
 .Op Fl b Ar base-dir
 .Op Fl c Ar comment
@@ -59,6 +60,7 @@
 .Op Fl g Ar gid/name/=uid
 .Op Fl k Ar skel-dir
 .Op Fl L Ar login-class
+.Op Fl M Ar home-perm
 .Op Fl p Ar password
 .Op Fl r Ar lowuid..highuid
 .Op Fl s Ar shell
@@ -109,18 +111,13 @@
 utility exits 0 on success, and \*[Gt]0 if an error occurs.
 .Sh FILES
 .Bl -tag -width /usr/share/examples/usermgmt -compact
-.It Pa /etc/skel/.[A-z]*
+.It Pa /etc/skel
 Skeleton files for new user
 .It Pa /etc/usermgmt.conf
 Configuration file for
 .Nm ,
 .Xr group 8
 and those backend commands
-.It Pa /usr/share/examples/usermgmt
-A directory containing examples for
-.Nm
-and
-.Xr group 8
 .El
 .Sh SEE ALSO
 .Xr chpass 1 ,
Index: user.c
===================================================================
RCS file: /cvsroot/src/usr.sbin/user/user.c,v
retrieving revision 1.79
diff -u -r1.79 user.c
--- user.c	5 Apr 2005 22:54:26 -0000	1.79
+++ user.c	27 May 2005 12:22:14 -0000
@@ -1,6 +1,7 @@
 /* $NetBSD: user.c,v 1.79 2005/04/05 22:54:26 agc Exp $ */
 
 /*
+ * Copyright (c) 2005 Hubert Feyrer <hubert@feyrer.de>. All rights reserved.
  * Copyright (c) 1999 Alistair G. Crooks.  All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -14,6 +15,8 @@
  * 3. All advertising materials mentioning features or use of this software
  *    must display the following acknowledgement:
  *	This product includes software developed by Alistair G. Crooks.
+ *	This product includes software developed for The NetBSD Foundation
+ *        by Hubert Feyrer <hubert@feyrer.de>.
  * 4. The name of the author may not be used to endorse or promote
  *    products derived from this software without specific prior written
  *    permission.
@@ -76,6 +79,7 @@
 	char	       *u_password;		/* encrypted password */
 	char	       *u_comment;		/* comment field */
 	char	       *u_home;			/* home directory */
+	mode_t		u_homeperm;		/* permissions of home dir */
 	char	       *u_primgrp;		/* primary group */
 	int		u_groupc;		/* # of secondary groups */
 	const char     *u_groupv[NGROUPS_MAX];	/* secondary groups */
@@ -152,6 +156,10 @@
 #define DEF_CLASS	""
 #endif
 
+#ifndef DEF_HOMEPERM
+#define DEF_HOMEPERM	0755
+#endif
+
 #ifndef WAITSECS
 #define WAITSECS	10
 #endif
@@ -376,7 +384,7 @@
 
 /* copy any dot files into the user's home directory */
 static int
-copydotfiles(char *skeldir, int uid, int gid, char *dir)
+copydotfiles(char *skeldir, int uid, int gid, char *dir, mode_t homeperm)
 {
 	struct dirent	*dp;
 	DIR		*dirp;
@@ -402,6 +410,9 @@
 	}
 	(void) asystem("%s -R -h %d:%d %s", CHOWN, uid, gid, dir);
 	(void) asystem("%s -R u+w %s", CHMOD, dir);
+#ifdef EXTENSIONS
+	(void) asystem("%s 0%o %s", CHMOD, homeperm, dir);
+#endif	
 	return n;
 }
 
@@ -748,6 +759,7 @@
 	    fprintf(fp, "shell\t\t%s\n", up->u_shell) <= 0 ||
 #ifdef EXTENSIONS
 	    fprintf(fp, "class\t\t%s\n", up->u_class) <= 0 ||
+	    fprintf(fp, "homeperm\t0%o\n", up->u_homeperm) <= 0 ||
 #endif
 	    fprintf(fp, "inactive\t%s\n", (up->u_inactive == NULL) ?  UNSET_INACTIVE : up->u_inactive) <= 0 ||
 	    fprintf(fp, "expire\t\t%s\n", (up->u_expire == NULL) ?  UNSET_EXPIRY : up->u_expire) <= 0 ||
@@ -824,6 +836,12 @@
 				}
 				memsave(&up->u_class, cp, strlen(cp));
 #endif
+#ifdef EXTENSIONS
+			} else if (strncmp(s, "homeperm", 8) == 0) {
+				for (cp = s + 8 ; *cp && isspace(*cp) ; cp++) {
+				}
+				up->u_homeperm=strtoul(cp, NULL, 8);
+#endif
 			} else if (strncmp(s, "inactive", 8) == 0) {
 				for (cp = s + 8 ; *cp && isspace(*cp) ; cp++) {
 				}
@@ -1112,7 +1130,7 @@
 				pw_abort();
 				err(EXIT_FAILURE, "can't mkdir `%s'", home);
 			}
-			(void) copydotfiles(up->u_skeldir, up->u_uid, gid, home);
+			(void) copydotfiles(up->u_skeldir, up->u_uid, gid, home, up->u_homeperm);
 		}
 	}
 	if (strcmp(up->u_primgrp, "=uid") == 0 &&
@@ -1503,12 +1521,12 @@
 {
 	if (strcmp(prog, "useradd") == 0) {
 		(void) fprintf(stderr, "usage: %s -D [-b basedir] [-e expiry] "
-		    "[-f inactive] [-g group]\n\t[-r lowuid..highuid] "
+		    "[-f inactive] [-g group]\n\t[-M homeperm] [-r lowuid..highuid] "
 		    "[-s shell] [-L class]\n", prog);
 		(void) fprintf(stderr, "usage: %s [-G group] [-b basedir] "
 		    "[-c comment] [-d homedir] [-e expiry]\n\t[-f inactive] "
-		    "[-g group] [-k skeletondir] [-m] [-o] [-p password]\n"
-		    "\t[-r lowuid..highuid] [-s shell]\n\t[-u uid] [-v] user\n",
+		    "[-g group] [-k skeletondir] [-m] [-M homeperm] [-o]\n"
+		    "\t[-p password] [-r lowuid..highuid] [-s shell]\n\t[-u uid] [-v] user\n",
 		    prog);
 	} else if (strcmp(prog, "usermod") == 0) {
 		(void) fprintf(stderr, "usage: %s [-G group] [-c comment] "
@@ -1544,7 +1562,7 @@
 }
 
 #ifdef EXTENSIONS
-#define ADD_OPT_EXTENSIONS	"p:r:vL:S"
+#define ADD_OPT_EXTENSIONS	"L:M:p:r:Sv"
 #else
 #define ADD_OPT_EXTENSIONS	
 #endif
@@ -1561,6 +1579,7 @@
 #endif
 
 	(void) memset(&u, 0, sizeof(u));
+	u.u_homeperm = DEF_HOMEPERM;
 	read_defaults(&u);
 	u.u_uid = -1;
 	defaultfield = bigD = 0;
@@ -1618,6 +1637,12 @@
 			memsave(&u.u_class, optarg, strlen(optarg));
 			break;
 #endif
+#ifdef EXTENSIONS
+		case 'M':
+			defaultfield = 1;
+			u.u_homeperm = strtol(optarg, NULL, 8);
+			break;
+#endif
 		case 'm':
 			u.u_flags |= F_MKDIR;
 			break;
@@ -1666,6 +1691,7 @@
 		(void) printf("shell\t\t%s\n", u.u_shell);
 #ifdef EXTENSIONS
 		(void) printf("class\t\t%s\n", u.u_class);
+		(void) printf("homeperm\t0%o\n", u.u_homeperm);
 #endif
 		(void) printf("inactive\t%s\n", (u.u_inactive == NULL) ? UNSET_INACTIVE : u.u_inactive);
 		(void) printf("expire\t\t%s\n", (u.u_expire == NULL) ? UNSET_EXPIRY : u.u_expire);
Index: useradd.8
===================================================================
RCS file: /cvsroot/src/usr.sbin/user/useradd.8,v
retrieving revision 1.30
diff -u -r1.30 useradd.8
--- useradd.8	5 Feb 2005 15:28:46 -0000	1.30
+++ useradd.8	27 May 2005 12:22:15 -0000
@@ -31,7 +31,7 @@
 .\" SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 .\"
 .\"
-.Dd January 14, 2004
+.Dd May 27, 2005
 .Dt USERADD 8
 .Os
 .Sh NAME
@@ -45,14 +45,15 @@
 .Op Fl f Ar inactive-time
 .Oo
 .Fl g Ar gid | name | Li =uid Oc
-.Op Fl L Ar login-class
 .Op Fl k Ar skel-dir
+.Op Fl L Ar login-class
+.Op Fl M Ar home-perm
 .Oo
 .Fl r Ar lowuid Ns Li .. Ns Ar highuid
 .Oc
 .Op Fl s Ar shell
 .Nm
-.Op Fl Smov
+.Op Fl moSv
 .Op Fl G Ar secondary-group
 .Op Fl b Ar base-dir
 .Op Fl c Ar comment
@@ -63,6 +64,7 @@
 .Fl g Ar gid | name | Li =uid Oc
 .Op Fl k Ar skel-dir
 .Op Fl L Ar login-class
+.Op Fl M Ar home-perm
 .Op Fl p Ar password
 .Oo
 .Fl r Ar lowuid Ns Li .. Ns Ar highuid
@@ -147,6 +149,13 @@
 See
 .Xr login.conf 5
 for more information on user login classes.
+.It Fl M Ar home-perm
+sets the default permissions of the newly created home directory
+if
+.Fl m
+is given.
+The permission is specified as octal number, with or
+without a leading '0'.
 .It Xo
 .Fl r Ar lowuid Ns Li .. Ns Ar highuid
 .Xc
@@ -216,6 +225,13 @@
 See
 .Xr login.conf 5
 for more information on user login classes.
+.It Fl M Ar home-perm
+sets the permissions of the newly created home directory
+if
+.Fl m
+is given.
+The permission is specified as octal number, with or
+without a leading '0'.
 .It Fl m
 create a new home directory for the new user.
 .It Fl o
@@ -256,7 +272,7 @@
 .Sh FILES
 .Bl -tag -width /etc/usermgmt.conf -compact
 .It Pa /etc/usermgmt.conf
-.It Pa /etc/skel/*
+.It Pa /etc/skel
 .It Pa /etc/login.conf
 .El
 .Sh SEE ALSO
@@ -276,7 +292,8 @@
 .Nx 1.5 .
 It is based on the
 .Ar addnerd
-package by the same author.
+package by the same author. Support for setting permissions of home
+directories was added by Hubert Feyrer.
 .Sh AUTHORS
 The
 .Nm
Index: usermgmt.conf.5
===================================================================
RCS file: /cvsroot/src/usr.sbin/user/usermgmt.conf.5,v
retrieving revision 1.3
diff -u -r1.3 usermgmt.conf.5
--- usermgmt.conf.5	2 Oct 2002 13:49:11 -0000	1.3
+++ usermgmt.conf.5	27 May 2005 12:22:15 -0000
@@ -29,7 +29,7 @@
 .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 .\" SUCH DAMAGE.
 .\"
-.Dd May 28, 2002
+.Dd May 27, 2005
 .Dt USERMGMT.CONF 5
 .Os
 .\" turn off hyphenation
@@ -91,6 +91,14 @@
 .Ic group
 .Ar gid | name | Li =uid
 .Ed
+.It Ic homeperm
+sets the default permissions of the newly created home directory
+if
+.Fl m
+is given to
+.Xr useradd 8 .
+The permission is specified as octal number, with or
+without a leading '0'.
 .It Ic inactive
 sets the default time at which new accounts expire.
 A value of 0 can be used to disable this feature.

>Unformatted: