diff options
Diffstat (limited to 'umount.c')
-rw-r--r-- | umount.c | 72 |
1 files changed, 64 insertions, 8 deletions
@@ -28,6 +28,14 @@ | |||
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 | |||
31 | static const char umount_usage[] = | 39 | static const char umount_usage[] = |
32 | "Usage: umount [flags] filesystem|directory\n\n" | 40 | "Usage: umount [flags] filesystem|directory\n\n" |
33 | "Flags:\n" | 41 | "Flags:\n" |
@@ -44,23 +52,54 @@ static int useMtab = TRUE; | |||
44 | static int umountAll = FALSE; | 52 | static int umountAll = FALSE; |
45 | extern const char mtab_file[]; /* Defined in utility.c */ | 53 | extern const char mtab_file[]; /* Defined in utility.c */ |
46 | 54 | ||
47 | #if ! defined BB_MTAB | ||
48 | #define do_umount( blockDevice, useMtab) umount( blockDevice) | ||
49 | #else | ||
50 | static int | 55 | static int |
51 | do_umount(const char* name, int useMtab) | 56 | do_umount(const char* name, int useMtab) |
52 | { | 57 | { |
53 | int status = umount(name); | 58 | int status; |
59 | |||
60 | #if defined BB_FEATURE_MOUNT_LOOP | ||
61 | /* check to see if this is a loop device */ | ||
62 | struct stat fst; | ||
63 | char dev[20]; | ||
64 | const char *oldname = NULL; | ||
65 | int i; | ||
66 | |||
67 | if (stat(name, &fst)) { | ||
68 | fprintf(stderr, "umount: %s: %s\n", name, strerror(errno)); | ||
69 | exit(1); | ||
70 | } | ||
71 | for (i = 0 ; i <= 7 ; i++) { | ||
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 | } | ||
81 | } | ||
82 | #endif | ||
83 | |||
84 | status = umount(name); | ||
54 | 85 | ||
86 | #if defined BB_FEATURE_MOUNT_LOOP | ||
87 | if (!strncmp("/dev/loop", name, 9)) { /* this was a loop device, delete it */ | ||
88 | del_loop(name); | ||
89 | if (oldname != NULL) | ||
90 | name = oldname; | ||
91 | } | ||
92 | #endif | ||
93 | #if defined BB_MTAB | ||
55 | if ( status == 0 ) { | 94 | if ( status == 0 ) { |
56 | if ( useMtab==TRUE ) | 95 | if ( useMtab==TRUE ) |
57 | erase_mtab(name); | 96 | erase_mtab(name); |
58 | return 0; | 97 | return 0; |
59 | } | 98 | } |
60 | else | 99 | else |
61 | return( status); | ||
62 | } | ||
63 | #endif | 100 | #endif |
101 | return(status); | ||
102 | } | ||
64 | 103 | ||
65 | static int | 104 | static int |
66 | umount_all(int useMtab) | 105 | umount_all(int useMtab) |
@@ -135,7 +174,24 @@ umount_main(int argc, char** argv) | |||
135 | exit (TRUE); | 174 | exit (TRUE); |
136 | else { | 175 | else { |
137 | perror("umount"); | 176 | perror("umount"); |
138 | exit( FALSE); | 177 | exit(FALSE); |
139 | } | 178 | } |
140 | } | 179 | } |
141 | 180 | ||
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 | ||