[prev in list] [next in list] [prev in thread] [next in thread] 

List:       busybox
Subject:    [PATCH] install -D
From:       Natanael Copa <natanael.copa () gmail ! com>
Date:       2008-06-25 10:03:40
Message-ID: 1214388220.17866.5.camel () nc ! nor ! wtbts ! org
[Download RAW message or body]

Attatched is a patch that enables -D option to install.

btw, busybox's current behaviour is different from GNU coreutils:

# busybox install -o nobody -g nobody -d /foo/bar/baznc && find /foo | xargs ls -ld
drwxrwxrwx 3 nobody nobody 16 Jun 25 09:29 /foo
drwxrwxrwx 3 nobody nobody 16 Jun 25 09:29 /foo/bar
drwxrwxrwx 2 nobody nobody  6 Jun 25 09:29 /foo/bar/baz
# rm -rf /foo
# install -o nobody -g nobody -d /foo/bar/baz && find /foo | xargs ls -ld
drwxr-xr-x 3 root   root   16 Jun 25 09:31 /foo
drwxr-xr-x 3 root   root   16 Jun 25 09:31 /foo/bar
drwxr-xr-x 2 nobody nobody  6 Jun 25 09:31 /foo/bar/baz

patch does not fix this.

-nc

["busybox-svn-install-D.patch" (busybox-svn-install-D.patch)]

Index: coreutils/install.c
===================================================================
--- coreutils/install.c	(revision 22496)
+++ coreutils/install.c	(working copy)
@@ -20,6 +20,7 @@
 	"group\0"               No_argument       "g"
 	"mode\0"                No_argument       "m"
 	"owner\0"               No_argument       "o"
+	"\0"                    No_argument       "D"
 /* autofs build insists of using -b --suffix=.orig */
 /* TODO? (short option for --suffix is -S) */
 #if ENABLE_SELINUX
@@ -63,6 +64,36 @@
 
 #endif
 
+static int create_dirs_with_owner(char *path, int mode, int setowner, int uid, int gid, int skiplast)
+{
+	int ret = 0;
+	char *slash = path;
+	while (1) {
+		slash = strchr(slash + 1, '/');
+		if (slash) {
+			*slash = '\0';
+		} else if (skiplast) {
+			break;
+		}
+		if (mkdir(path, mode | 0111) == -1) {
+			if (errno != EEXIST) {
+				bb_perror_msg("cannot create %s", path);
+				ret = EXIT_FAILURE;
+				break;
+			}
+		} /* dir was created, chown? */
+		else if (setowner && lchown(path, uid, gid) == -1) {
+			bb_perror_msg("cannot change ownership of %s", path);
+			ret = EXIT_FAILURE;
+			break;
+		}
+		if (!slash)
+			break;
+		*slash = '/';
+	}
+	return ret;
+}
+
 int install_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
 int install_main(int argc, char **argv)
 {
@@ -92,9 +123,10 @@
 		OPT_GROUP         = 1 << 6,
 		OPT_MODE          = 1 << 7,
 		OPT_OWNER         = 1 << 8,
+		OPT_MKDIRDEST	  = 1 << 9,
 #if ENABLE_SELINUX
-		OPT_SET_SECURITY_CONTEXT = 1 << 9,
-		OPT_PRESERVE_SECURITY_CONTEXT = 1 << 10,
+		OPT_SET_SECURITY_CONTEXT = 1 << 10,
+		OPT_PRESERVE_SECURITY_CONTEXT = 1 << 11,
 #endif
 	};
 
@@ -105,7 +137,7 @@
 	/* -c exists for backwards compatibility, it's needed */
 	/* -v is ignored ("print name of each created directory") */
 	/* -b is ignored ("make a backup of each existing destination file") */
-	flags = getopt32(argv, "cvb" "dpsg:m:o:" USE_SELINUX("Z:"),
+	flags = getopt32(argv, "cvb" "dpsg:m:o:D" USE_SELINUX("Z:"),
 			&gid_str, &mode_str, &uid_str USE_SELINUX(, &scontext));
 	argc -= optind;
 	argv += optind;
@@ -142,29 +174,10 @@
 	 */
 	if (flags & OPT_DIRECTORY) {
 		while ((arg = *argv++) != NULL) {
-			char *slash = arg;
-			while (1) {
-				slash = strchr(slash + 1, '/');
-				if (slash)
-					*slash = '\0';
-				if (mkdir(arg, mode | 0111) == -1) {
-					if (errno != EEXIST) {
-						bb_perror_msg("cannot create %s", arg);
-						ret = EXIT_FAILURE;
-						break;
-					}
-				} /* dir was created, chown? */
-				else if ((flags & (OPT_OWNER|OPT_GROUP))
-				 && lchown(arg, uid, gid) == -1
-				) {
-					bb_perror_msg("cannot change ownership of %s", arg);
-					ret = EXIT_FAILURE;
-					break;
-				}
-				if (!slash)
-					break;
-				*slash = '/';
-			}
+			int status = create_dirs_with_owner(arg, mode, 
+				flags & (OPT_OWNER|OPT_GROUP), uid, gid, 0);
+			if (status)
+				ret = status;
 		}
 		return ret;
 	}
@@ -181,6 +194,9 @@
 		char *dest = last;
 		if (isdir)
 			dest = concat_path_file(last, basename(arg));
+		if (flags & OPT_MKDIRDEST)
+			create_dirs_with_owner(dest, mode, 
+				flags & (OPT_OWNER|OPT_GROUP), uid, gid, 1);
 		if (copy_file(arg, dest, copy_flags)) {
 			/* copy is not made */
 			ret = EXIT_FAILURE;


_______________________________________________
busybox mailing list
busybox@busybox.net
http://busybox.net/cgi-bin/mailman/listinfo/busybox

[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic