X-Git-Url: https://git.cameronkatri.com/pw-darwin.git/blobdiff_plain/0c9f365da25caa3b04bcfe82b70ee49aab96e619..6a151c16645f90b21f171a44661b109f06e9097e:/pw/pwupd.c?ds=sidebyside

diff --git a/pw/pwupd.c b/pw/pwupd.c
index fb56dac..84226a9 100644
--- a/pw/pwupd.c
+++ b/pw/pwupd.c
@@ -22,10 +22,13 @@
  * 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.
- *
- *	$Id: pwupd.c,v 1.1.1.3 1996/12/10 23:59:02 joerg Exp $
  */
 
+#ifndef lint
+static const char rcsid[] =
+  "$FreeBSD$";
+#endif /* not lint */
+
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -34,20 +37,47 @@
 #include <errno.h>
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <sys/param.h>
 #include <sys/wait.h>
-#include <stdarg.h>
 
 #include "pwupd.h"
 
 #define HAVE_PWDB_C	1
+#define	HAVE_PWDB_U	1
 
-static int
+static char pathpwd[] = _PATH_PWD;
+static char * pwpath = pathpwd;
+ 
+int
+setpwdir(const char * dir)
+{
+	if (dir == NULL)
+		return -1;
+	else {
+		char * d = malloc(strlen(dir)+1);
+		if (d == NULL)
+			return -1;
+		pwpath = strcpy(d, dir);
+	}
+	return 0;
+}
+
+char *
+getpwpath(char const * file)
+{
+	static char pathbuf[MAXPATHLEN];
+
+	snprintf(pathbuf, sizeof pathbuf, "%s/%s", pwpath, file);
+	return pathbuf;
+}
+
+int
 pwdb(char *arg,...)
 {
 	int             i = 0;
 	pid_t           pid;
 	va_list         ap;
-	char           *args[8];
+	char           *args[10];
 
 	args[i++] = _PATH_PWD_MKDB;
 	va_start(ap, arg);
@@ -55,18 +85,22 @@ pwdb(char *arg,...)
 		args[i++] = arg;
 		arg = va_arg(ap, char *);
 	}
-	args[i++] = _PATH_MASTERPASSWD;
+	if (pwpath != pathpwd) {
+		args[i++] = "-d";
+		args[i++] = pwpath;
+	}
+	args[i++] = getpwpath(_MASTERPASSWD);
 	args[i] = NULL;
 
 	if ((pid = fork()) == -1)	/* Error (errno set) */
-		i = -1;
+		i = errno;
 	else if (pid == 0) {	/* Child */
 		execv(args[0], args);
 		_exit(1);
 	} else {		/* Parent */
 		waitpid(pid, &i, 0);
-		if ((i = WEXITSTATUS(i)) != 0)
-			errno = EIO;	/* set SOMETHING */
+		if (WEXITSTATUS(i))
+			i = EIO;
 	}
 	return i;
 }
@@ -77,7 +111,8 @@ fmtpwentry(char *buf, struct passwd * pwd, int type)
 	int             l;
 	char           *pw;
 
-	pw = (pwd->pw_passwd == NULL || !*pwd->pw_passwd) ? "" : (type == PWF_MASTER) ? pwd->pw_passwd : "*";
+	pw = (type == PWF_MASTER) ?
+	    ((pwd->pw_passwd == NULL) ? "" : pwd->pw_passwd) : "*";
 
 	if (type == PWF_PASSWD)
 		l = sprintf(buf, "%s:*:%ld:%ld:%s:%s:%s\n",
@@ -106,20 +141,23 @@ pw_update(struct passwd * pwd, char const * user, int mode)
 {
 	int             rc = 0;
 
-	endpwent();
+	ENDPWENT();
 
 	/*
 	 * First, let's check the see if the database is alright
-	 * Note: -c is only available in FreeBSD 2.2 and above
+	 * Note: -C is only available in FreeBSD 2.2 and above
 	 */
 #ifdef HAVE_PWDB_C
-	if (pwdb("-c", NULL) == 0) {	/* Check only */
+	if (pwdb("-C", NULL) == 0) {	/* Check only */
 #else
-	{				/* No -c */
+	{				/* No -C */
 #endif
-		char            pfx[32];
+		char            pfx[PWBUFSZ];
 		char            pwbuf[PWBUFSZ];
-		int             l = sprintf(pfx, "%s:", user);
+		int             l = snprintf(pfx, PWBUFSZ, "%s:", user);
+#ifdef HAVE_PWDB_U
+		int		isrename = pwd!=NULL && strcmp(user, pwd->pw_name);
+#endif
 
 		/*
 		 * Update the passwd file first
@@ -128,15 +166,28 @@ pw_update(struct passwd * pwd, char const * user, int mode)
 			*pwbuf = '\0';
 		else
 			fmtpwentry(pwbuf, pwd, PWF_PASSWD);
-		if ((rc = fileupdate(_PATH_PASSWD, 0644, pwbuf, pfx, l, mode)) != 0) {
+
+		if (l < 0)
+			l = 0;
+		rc = fileupdate(getpwpath(_PASSWD), 0644, pwbuf, pfx, l, mode);
+		if (rc == 0) {
 
 			/*
 			 * Then the master.passwd file
 			 */
 			if (pwd != NULL)
 				fmtpwentry(pwbuf, pwd, PWF_MASTER);
-			if ((rc = fileupdate(_PATH_MASTERPASSWD, 0644, pwbuf, pfx, l, mode)) != 0)
-				rc = pwdb(NULL) == 0;
+			rc = fileupdate(getpwpath(_MASTERPASSWD), 0600, pwbuf, pfx, l, mode);
+			if (rc == 0) {
+#ifdef HAVE_PWDB_U
+				if (mode == UPD_DELETE || isrename)
+#endif
+					rc = pwdb(NULL);
+#ifdef HAVE_PWDB_U
+				else
+					rc = pwdb("-u", user, NULL);
+#endif
+			}
 		}
 	}
 	return rc;