diff options
Diffstat (limited to 'umount.c')
-rw-r--r-- | umount.c | 70 |
1 files changed, 18 insertions, 52 deletions
@@ -28,14 +28,6 @@ | |||
28 | #include <fstab.h> | 28 | #include <fstab.h> |
29 | #include <errno.h> | 29 | #include <errno.h> |
30 | 30 | ||
31 | #if defined BB_FEATURE_MOUNT_LOOP | ||
32 | #include <fcntl.h> | ||
33 | #include <sys/ioctl.h> | ||
34 | #include <linux/loop.h> | ||
35 | |||
36 | static int del_loop(const char *device); | ||
37 | #endif | ||
38 | |||
39 | static const char umount_usage[] = | 31 | static const char umount_usage[] = |
40 | "umount [flags] filesystem|directory\n\n" | 32 | "umount [flags] filesystem|directory\n\n" |
41 | "Flags:\n" | 33 | "Flags:\n" |
@@ -52,43 +44,34 @@ static int useMtab = TRUE; | |||
52 | static int umountAll = FALSE; | 44 | static int umountAll = FALSE; |
53 | extern const char mtab_file[]; /* Defined in utility.c */ | 45 | extern const char mtab_file[]; /* Defined in utility.c */ |
54 | 46 | ||
47 | #define MIN(x,y) (x > y ? x : y) | ||
48 | |||
55 | static int | 49 | static int |
56 | do_umount(const char* name, int useMtab) | 50 | do_umount(const char* name, int useMtab) |
57 | { | 51 | { |
58 | int status; | 52 | int status; |
59 | 53 | struct mntent *m; | |
60 | #if defined BB_FEATURE_MOUNT_LOOP | 54 | FILE *mountTable; |
61 | /* check to see if this is a loop device */ | 55 | const char *blockDevice = NULL; |
62 | struct stat fst; | 56 | |
63 | char dev[20]; | 57 | if ((mountTable = setmntent (mtab_file, "r"))) { |
64 | const char *oldname = NULL; | 58 | while ((m = getmntent (mountTable)) != 0) { |
65 | int i; | 59 | if (strncmp(m->mnt_dir, name, |
66 | 60 | MIN(strlen(m->mnt_dir),strlen(name))) == 0) | |
67 | if (stat(name, &fst)) { | 61 | blockDevice = m->mnt_fsname; |
68 | fprintf(stderr, "umount: %s: %s\n", name, strerror(errno)); | 62 | else if (strcmp(m->mnt_fsname, name) == 0) { |
69 | exit(1); | 63 | blockDevice = name; |
70 | } | 64 | name = m->mnt_dir; |
71 | for (i = 0 ; i <= 7 ; i++) { | 65 | } |
72 | struct stat lst; | ||
73 | sprintf(dev, "/dev/loop%d", i); | ||
74 | if (stat(dev, &lst)) | ||
75 | continue; | ||
76 | if (lst.st_dev == fst.st_dev) { | ||
77 | oldname = name; | ||
78 | name = dev; | ||
79 | break; | ||
80 | } | 66 | } |
81 | } | 67 | } |
82 | #endif | ||
83 | 68 | ||
84 | status = umount(name); | 69 | status = umount(name); |
85 | 70 | ||
86 | #if defined BB_FEATURE_MOUNT_LOOP | 71 | #if defined BB_FEATURE_MOUNT_LOOP |
87 | if (!strncmp("/dev/loop", name, 9)) { /* this was a loop device, delete it */ | 72 | if (blockDevice != NULL && !strncmp("/dev/loop", blockDevice, 9)) |
88 | del_loop(name); | 73 | /* this was a loop device, delete it */ |
89 | if (oldname != NULL) | 74 | del_loop(blockDevice); |
90 | name = oldname; | ||
91 | } | ||
92 | #endif | 75 | #endif |
93 | #if defined BB_MTAB | 76 | #if defined BB_MTAB |
94 | if ( status == 0 ) { | 77 | if ( status == 0 ) { |
@@ -178,20 +161,3 @@ umount_main(int argc, char** argv) | |||
178 | } | 161 | } |
179 | } | 162 | } |
180 | 163 | ||
181 | #if defined BB_FEATURE_MOUNT_LOOP | ||
182 | static int del_loop(const char *device) | ||
183 | { | ||
184 | int fd; | ||
185 | |||
186 | if ((fd = open(device, O_RDONLY)) < 0) { | ||
187 | perror(device); | ||
188 | exit(1); | ||
189 | } | ||
190 | if (ioctl(fd, LOOP_CLR_FD, 0) < 0) { | ||
191 | perror("ioctl: LOOP_CLR_FD"); | ||
192 | exit(1); | ||
193 | } | ||
194 | close(fd); | ||
195 | return(0); | ||
196 | } | ||
197 | #endif | ||