Changeset 1770 in MondoRescue for branches/stable/mindi-busybox/util-linux/switch_root.c
- Timestamp:
- Nov 6, 2007, 11:01:53 AM (16 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/stable/mindi-busybox/util-linux/switch_root.c
r821 r1770 1 /* vi: set ts=4:*/1 /* vi: set sw=4 ts=4: */ 2 2 /* Copyright 2005 Rob Landley <rob@landley.net> 3 3 * 4 4 * Switch from rootfs to another filesystem as the root of the mount tree. 5 5 * 6 * Licensed under GPL v2 or later, see file LICENSE in this tarball for details.6 * Licensed under GPL version 2, see file LICENSE in this tarball for details. 7 7 */ 8 8 9 #include "busybox.h" 10 #include <fcntl.h> 11 #include <string.h> 9 #include "libbb.h" 12 10 #include <sys/vfs.h> 13 #include <unistd.h>14 11 15 12 … … 28 25 #endif 29 26 30 dev_t rootdev;27 static dev_t rootdev; 31 28 32 29 // Recursively delete contents of rootfs. 33 30 34 static void delete_contents(c har *directory)31 static void delete_contents(const char *directory) 35 32 { 36 33 DIR *dir; … … 39 36 40 37 // Don't descend into other filesystems 41 if (lstat(directory, &st) || st.st_dev != rootdev) return;38 if (lstat(directory, &st) || st.st_dev != rootdev) return; 42 39 43 40 // Recursively delete the contents of directories. 44 41 if (S_ISDIR(st.st_mode)) { 45 if((dir = opendir(directory))) { 42 dir = opendir(directory); 43 if (dir) { 46 44 while ((d = readdir(dir))) { 47 char *newdir =d->d_name;45 char *newdir = d->d_name; 48 46 49 47 // Skip . and .. 50 if (*newdir=='.' && (!newdir[1] || (newdir[1]=='.' && !newdir[2])))48 if (*newdir=='.' && (!newdir[1] || (newdir[1]=='.' && !newdir[2]))) 51 49 continue; 52 50 … … 67 65 } 68 66 69 int switch_root_main(int argc, char *argv[]) 67 int switch_root_main(int argc, char **argv); 68 int switch_root_main(int argc, char **argv) 70 69 { 71 char *newroot, *console =NULL;70 char *newroot, *console = NULL; 72 71 struct stat st1, st2; 73 72 struct statfs stfs; … … 75 74 // Parse args (-c console) 76 75 77 bb_opt_complementally="-2"; 78 bb_getopt_ulflags(argc,argv,"c:",&console); 76 opt_complementary = "-2"; 77 getopt32(argv, "c:", &console); 78 argv += optind; 79 79 80 80 // Change to new root directory and verify it's a different fs. 81 81 82 newroot =argv[optind++];82 newroot = *argv++; 83 83 84 if (chdir(newroot) || lstat(".", &st1) || lstat("/", &st2) || 85 st1.st_dev == st2.st_dev) 86 { 87 bb_error_msg_and_die("bad newroot %s",newroot); 84 xchdir(newroot); 85 if (lstat(".", &st1) || lstat("/", &st2) || st1.st_dev == st2.st_dev) { 86 bb_error_msg_and_die("bad newroot %s", newroot); 88 87 } 89 rootdev =st2.st_dev;88 rootdev = st2.st_dev; 90 89 91 90 // Additional sanity checks: we're about to rm -rf /, so be REALLY SURE 92 91 // we mean it. (I could make this a CONFIG option, but I would get email 93 // from all the people who WILL eat their filesystems s.)92 // from all the people who WILL eat their filesystems.) 94 93 95 94 if (lstat("/init", &st1) || !S_ISREG(st1.st_mode) || statfs("/", &stfs) || … … 107 106 // recalculate "." and ".." links. 108 107 109 if (mount(".", "/", NULL, MS_MOVE, NULL) || chroot(".") || chdir("/")) 110 bb_error_msg_and_die("moving root"); 108 if (mount(".", "/", NULL, MS_MOVE, NULL) || chroot(".")) 109 bb_error_msg_and_die("error moving root"); 110 xchdir("/"); 111 111 112 112 // If a new console specified, redirect stdin/stdout/stderr to that. … … 114 114 if (console) { 115 115 close(0); 116 if(open(console, O_RDWR) < 0) 117 bb_error_msg_and_die("Bad console '%s'",console); 116 xopen(console, O_RDWR); 118 117 dup2(0, 1); 119 118 dup2(0, 2); … … 121 120 122 121 // Exec real init. (This is why we must be pid 1.) 123 execv(argv[ optind],argv+optind);124 bb_ error_msg_and_die("Bad init '%s'",argv[optind]);122 execv(argv[0], argv); 123 bb_perror_msg_and_die("bad init %s", argv[0]); 125 124 }
Note:
See TracChangeset
for help on using the changeset viewer.