diff options
Diffstat (limited to 'archival')
-rw-r--r-- | archival/cpio.c | 52 | ||||
-rw-r--r-- | archival/libarchive/get_header_ar.c | 6 |
2 files changed, 57 insertions, 1 deletions
diff --git a/archival/cpio.c b/archival/cpio.c index f525419b8..7149782d7 100644 --- a/archival/cpio.c +++ b/archival/cpio.c | |||
@@ -38,6 +38,20 @@ | |||
38 | //config: depends on FEATURE_CPIO_O | 38 | //config: depends on FEATURE_CPIO_O |
39 | //config: help | 39 | //config: help |
40 | //config: Passthrough mode. Rarely used. | 40 | //config: Passthrough mode. Rarely used. |
41 | //config: | ||
42 | //config:config FEATURE_CPIO_IGNORE_DEVNO | ||
43 | //config: bool "Support --ignore-devno like GNU cpio" | ||
44 | //config: default y | ||
45 | //config: depends on FEATURE_CPIO_O && LONG_OPTS | ||
46 | //config: help | ||
47 | //config: Optionally ignore device numbers when creating archives. | ||
48 | //config: | ||
49 | //config:config FEATURE_CPIO_RENUMBER_INODES | ||
50 | //config: bool "Support --renumber-inodes like GNU cpio" | ||
51 | //config: default y | ||
52 | //config: depends on FEATURE_CPIO_O && LONG_OPTS | ||
53 | //config: help | ||
54 | //config: Optionally renumber inodes when creating archives. | ||
41 | 55 | ||
42 | //applet:IF_CPIO(APPLET(cpio, BB_DIR_BIN, BB_SUID_DROP)) | 56 | //applet:IF_CPIO(APPLET(cpio, BB_DIR_BIN, BB_SUID_DROP)) |
43 | 57 | ||
@@ -75,6 +89,12 @@ | |||
75 | //usage: "\n -R USER[:GRP] Set owner of created files" | 89 | //usage: "\n -R USER[:GRP] Set owner of created files" |
76 | //usage: "\n -L Dereference symlinks" | 90 | //usage: "\n -L Dereference symlinks" |
77 | //usage: "\n -0 NUL terminated input" | 91 | //usage: "\n -0 NUL terminated input" |
92 | //usage: IF_FEATURE_CPIO_IGNORE_DEVNO( | ||
93 | //usage: "\n --ignore-devno" | ||
94 | //usage: ) | ||
95 | //usage: IF_FEATURE_CPIO_RENUMBER_INODES( | ||
96 | //usage: "\n --renumber-inodes" | ||
97 | //usage: ) | ||
78 | 98 | ||
79 | /* GNU cpio 2.9 --help (abridged): | 99 | /* GNU cpio 2.9 --help (abridged): |
80 | 100 | ||
@@ -162,17 +182,22 @@ enum { | |||
162 | IF_FEATURE_CPIO_P(OPTBIT_PASSTHROUGH,) | 182 | IF_FEATURE_CPIO_P(OPTBIT_PASSTHROUGH,) |
163 | IF_LONG_OPTS( OPTBIT_QUIET ,) | 183 | IF_LONG_OPTS( OPTBIT_QUIET ,) |
164 | IF_LONG_OPTS( OPTBIT_2STDOUT ,) | 184 | IF_LONG_OPTS( OPTBIT_2STDOUT ,) |
185 | IF_FEATURE_CPIO_IGNORE_DEVNO(OPTBIT_IGNORE_DEVNO,) | ||
186 | IF_FEATURE_CPIO_RENUMBER_INODES(OPTBIT_RENUMBER_INODES,) | ||
165 | OPT_CREATE = IF_FEATURE_CPIO_O((1 << OPTBIT_CREATE )) + 0, | 187 | OPT_CREATE = IF_FEATURE_CPIO_O((1 << OPTBIT_CREATE )) + 0, |
166 | OPT_FORMAT = IF_FEATURE_CPIO_O((1 << OPTBIT_FORMAT )) + 0, | 188 | OPT_FORMAT = IF_FEATURE_CPIO_O((1 << OPTBIT_FORMAT )) + 0, |
167 | OPT_PASSTHROUGH = IF_FEATURE_CPIO_P((1 << OPTBIT_PASSTHROUGH)) + 0, | 189 | OPT_PASSTHROUGH = IF_FEATURE_CPIO_P((1 << OPTBIT_PASSTHROUGH)) + 0, |
168 | OPT_QUIET = IF_LONG_OPTS( (1 << OPTBIT_QUIET )) + 0, | 190 | OPT_QUIET = IF_LONG_OPTS( (1 << OPTBIT_QUIET )) + 0, |
169 | OPT_2STDOUT = IF_LONG_OPTS( (1 << OPTBIT_2STDOUT )) + 0, | 191 | OPT_2STDOUT = IF_LONG_OPTS( (1 << OPTBIT_2STDOUT )) + 0, |
192 | OPT_IGNORE_DEVNO = IF_FEATURE_CPIO_IGNORE_DEVNO((1 << OPTBIT_IGNORE_DEVNO)) + 0, | ||
193 | OPT_RENUMBER_INODES = IF_FEATURE_CPIO_RENUMBER_INODES((1 << OPTBIT_RENUMBER_INODES)) + 0, | ||
170 | }; | 194 | }; |
171 | 195 | ||
172 | #define OPTION_STR "it0uvdmLF:R:" | 196 | #define OPTION_STR "it0uvdmLF:R:" |
173 | 197 | ||
174 | struct globals { | 198 | struct globals { |
175 | struct bb_uidgid_t owner_ugid; | 199 | struct bb_uidgid_t owner_ugid; |
200 | ino_t next_inode; | ||
176 | } FIX_ALIASING; | 201 | } FIX_ALIASING; |
177 | #define G (*(struct globals*)bb_common_bufsiz1) | 202 | #define G (*(struct globals*)bb_common_bufsiz1) |
178 | void BUG_cpio_globals_too_big(void); | 203 | void BUG_cpio_globals_too_big(void); |
@@ -206,6 +231,9 @@ static NOINLINE int cpio_o(void) | |||
206 | struct inodes_s *next; | 231 | struct inodes_s *next; |
207 | struct name_s *names; | 232 | struct name_s *names; |
208 | struct stat st; | 233 | struct stat st; |
234 | #if ENABLE_FEATURE_CPIO_RENUMBER_INODES | ||
235 | ino_t mapped_inode; | ||
236 | #endif | ||
209 | }; | 237 | }; |
210 | 238 | ||
211 | struct inodes_s *links = NULL; | 239 | struct inodes_s *links = NULL; |
@@ -260,6 +288,10 @@ static NOINLINE int cpio_o(void) | |||
260 | l = xzalloc(sizeof(*l)); | 288 | l = xzalloc(sizeof(*l)); |
261 | l->st = st; | 289 | l->st = st; |
262 | l->next = links; | 290 | l->next = links; |
291 | #if ENABLE_FEATURE_CPIO_RENUMBER_INODES | ||
292 | if (option_mask32 & OPT_RENUMBER_INODES) | ||
293 | l->mapped_inode = ++G.next_inode; | ||
294 | #endif | ||
263 | links = l; | 295 | links = l; |
264 | break; | 296 | break; |
265 | } | 297 | } |
@@ -278,6 +310,11 @@ static NOINLINE int cpio_o(void) | |||
278 | free(line); | 310 | free(line); |
279 | continue; | 311 | continue; |
280 | } | 312 | } |
313 | #if ENABLE_FEATURE_CPIO_RENUMBER_INODES | ||
314 | else if (option_mask32 & OPT_RENUMBER_INODES) { | ||
315 | st.st_ino = ++G.next_inode; | ||
316 | } | ||
317 | #endif | ||
281 | } else { /* line == NULL: EOF */ | 318 | } else { /* line == NULL: EOF */ |
282 | next_link: | 319 | next_link: |
283 | if (links) { | 320 | if (links) { |
@@ -285,6 +322,10 @@ static NOINLINE int cpio_o(void) | |||
285 | st = links->st; | 322 | st = links->st; |
286 | name = links->names->name; | 323 | name = links->names->name; |
287 | links->names = links->names->next; | 324 | links->names = links->names->next; |
325 | #if ENABLE_FEATURE_CPIO_RENUMBER_INODES | ||
326 | if (links->mapped_inode) | ||
327 | st.st_ino = links->mapped_inode; | ||
328 | #endif | ||
288 | /* GNU cpio is reported to emit file data | 329 | /* GNU cpio is reported to emit file data |
289 | * only for the last instance. Mimic that. */ | 330 | * only for the last instance. Mimic that. */ |
290 | if (links->names == NULL) | 331 | if (links->names == NULL) |
@@ -304,6 +345,11 @@ static NOINLINE int cpio_o(void) | |||
304 | } | 345 | } |
305 | } | 346 | } |
306 | 347 | ||
348 | #if ENABLE_FEATURE_CPIO_IGNORE_DEVNO | ||
349 | if (option_mask32 & OPT_IGNORE_DEVNO) | ||
350 | st.st_dev = st.st_rdev = 0; | ||
351 | #endif | ||
352 | |||
307 | bytes += printf("070701" | 353 | bytes += printf("070701" |
308 | "%08X%08X%08X%08X%08X%08X%08X" | 354 | "%08X%08X%08X%08X%08X%08X%08X" |
309 | "%08X%08X%08X%08X" /* GNU cpio uses uppercase hex */ | 355 | "%08X%08X%08X%08X" /* GNU cpio uses uppercase hex */ |
@@ -379,6 +425,12 @@ int cpio_main(int argc UNUSED_PARAM, char **argv) | |||
379 | "null\0" No_argument "0" | 425 | "null\0" No_argument "0" |
380 | "quiet\0" No_argument "\xff" | 426 | "quiet\0" No_argument "\xff" |
381 | "to-stdout\0" No_argument "\xfe" | 427 | "to-stdout\0" No_argument "\xfe" |
428 | #if ENABLE_FEATURE_CPIO_IGNORE_DEVNO | ||
429 | "ignore-devno\0" No_argument "\xfd" | ||
430 | #endif | ||
431 | #if ENABLE_FEATURE_CPIO_RENUMBER_INODES | ||
432 | "renumber-inodes\0" No_argument "\xfc" | ||
433 | #endif | ||
382 | ; | 434 | ; |
383 | #endif | 435 | #endif |
384 | 436 | ||
diff --git a/archival/libarchive/get_header_ar.c b/archival/libarchive/get_header_ar.c index 3a19d6ff7..6bd897392 100644 --- a/archival/libarchive/get_header_ar.c +++ b/archival/libarchive/get_header_ar.c | |||
@@ -92,8 +92,12 @@ char FAST_FUNC get_header_ar(archive_handle_t *archive_handle) | |||
92 | /* Only size is always present, the rest may be missing in | 92 | /* Only size is always present, the rest may be missing in |
93 | * long filename pseudo file. Thus we decode the rest | 93 | * long filename pseudo file. Thus we decode the rest |
94 | * after dealing with long filename pseudo file. | 94 | * after dealing with long filename pseudo file. |
95 | * | ||
96 | * GNU binutils in deterministic mode hard codes mode to 0644 (NOT | ||
97 | * 0100644). AR archives can only contain files, so force file | ||
98 | * mode. | ||
95 | */ | 99 | */ |
96 | typed->mode = read_num(ar.formatted.mode, 8, sizeof(ar.formatted.mode)); | 100 | typed->mode = read_num(ar.formatted.mode, 8, sizeof(ar.formatted.mode)) | S_IFREG; |
97 | typed->gid = read_num(ar.formatted.gid, 10, sizeof(ar.formatted.gid)); | 101 | typed->gid = read_num(ar.formatted.gid, 10, sizeof(ar.formatted.gid)); |
98 | typed->uid = read_num(ar.formatted.uid, 10, sizeof(ar.formatted.uid)); | 102 | typed->uid = read_num(ar.formatted.uid, 10, sizeof(ar.formatted.uid)); |
99 | typed->mtime = read_num(ar.formatted.date, 10, sizeof(ar.formatted.date)); | 103 | typed->mtime = read_num(ar.formatted.date, 10, sizeof(ar.formatted.date)); |