Dont unlink when testing ! Always preserve creation date Disable the -p option its for modification date Remove some cpio header debugging noise Syncronise file listing behaviour with upstream.
No binary (build failed)
—
(log yok)
| @@ -40,8 +40,8 @@ extern int cpio_main(int argc, char **argv) | |
| archive_handle = init_handle(); | |
| archive_handle->src_fd = fileno(stdin); | |
| archive_handle->seek = seek_by_char; | |
| - | archive_handle->action_header = header_list; |
| - | |
| + | archive_handle->flags = ARCHIVE_EXTRACT_NEWER | ARCHIVE_PRESERVE_DATE; |
| + | |
| while ((opt = getopt(argc, argv, "idmuvtF:")) != -1) { | |
| switch (opt) { | |
| case 'i': /* extract */ | |
| @@ -50,17 +50,28 @@ extern int cpio_main(int argc, char **argv) | |
| case 'd': /* create _leading_ directories */ | |
| archive_handle->flags |= ARCHIVE_CREATE_LEADING_DIRS; | |
| break; | |
| + | #if 0 |
| case 'm': /* preserve modification time */ | |
| archive_handle->flags |= ARCHIVE_PRESERVE_DATE; | |
| break; | |
| + | #endif |
| case 'v': /* verbosly list files */ | |
| - | archive_handle->action_header = header_verbose_list; |
| + | if (archive_handle->action_header == header_list) { |
| + | archive_handle->action_header = header_verbose_list; |
| + | } else { |
| + | archive_handle->action_header = header_list; |
| + | } |
| break; | |
| case 'u': /* unconditional */ | |
| archive_handle->flags |= ARCHIVE_EXTRACT_UNCONDITIONAL; | |
| + | archive_handle->flags &= ~ARCHIVE_EXTRACT_NEWER; |
| break; | |
| case 't': /* list files */ | |
| - | archive_handle->action_header = header_list; |
| + | if (archive_handle->action_header == header_list) { |
| + | archive_handle->action_header = header_verbose_list; |
| + | } else { |
| + | archive_handle->action_header = header_list; |
| + | } |
| break; | |
| case 'F': | |
| archive_handle->src_fd = bb_xopen(optarg, O_RDONLY); | |
| @@ -81,4 +92,3 @@ extern int cpio_main(int argc, char **argv) | |
| return(EXIT_SUCCESS); | |
| } | |
| - | |
| @@ -39,6 +39,31 @@ extern void data_extract_all(archive_handle_t *archive_handle) | |
| free(name); | |
| } | |
| + | /* Check if the file already exists */ |
| + | if (archive_handle->flags & ARCHIVE_EXTRACT_UNCONDITIONAL) { |
| + | /* Remove the existing entry if it exists */ |
| + | if ((unlink(file_header->name) == -1) && (errno != ENOENT)) { |
| + | bb_perror_msg_and_die("Couldnt remove old file"); |
| + | } |
| + | } |
| + | else if (archive_handle->flags & ARCHIVE_EXTRACT_NEWER) { |
| + | /* Remove the existing entry if its older than the extracted entry */ |
| + | struct stat statbuf; |
| + | if ((lstat(file_header->name, &statbuf) == -1) && (errno != ENOENT)) { |
| + | bb_perror_msg_and_die("Couldnt stat old file"); |
| + | } |
| + | if (statbuf.st_mtime <= file_header->mtime) { |
| + | if (!(archive_handle->flags & ARCHIVE_EXTRACT_QUIET)) { |
| + | bb_error_msg("%s not created: newer or same age file exists", file_header->name); |
| + | } |
| + | data_skip(archive_handle); |
| + | return; |
| + | } |
| + | if ((unlink(file_header->name) == -1) && (errno != ENOENT)) { |
| + | bb_perror_msg_and_die("Couldnt remove old file"); |
| + | } |
| + | } |
| + | |
| /* Handle hard links seperately */ | |
| if (!S_ISLNK(file_header->mode) && (file_header->link_name) && (file_header->size == 0)) { | |
| /* hard link */ | |
| @@ -36,7 +36,6 @@ extern char get_header_cpio(archive_handle_t *archive_handle) | |
| int namesize; | |
| char dummy[16]; | |
| int major, minor, nlink, inode; | |
| - | char extract_flag; |
| if (pending_hardlinks) { /* Deal with any pending hardlinks */ | |
| hardlinks_t *tmp; | |
| @@ -71,17 +70,7 @@ extern char get_header_cpio(archive_handle_t *archive_handle) | |
| } | |
| archive_handle->offset += 110; | |
| - | if (strncmp(&cpio_header[0], "07070", 5) != 0) { |
| - | printf("cpio header is %x-%x-%x-%x-%x\n", |
| - | cpio_header[0], |
| - | cpio_header[1], |
| - | cpio_header[2], |
| - | cpio_header[3], |
| - | cpio_header[4]); |
| - | bb_error_msg_and_die("Unsupported cpio format"); |
| - | } |
| - | |
| - | if ((cpio_header[5] != '1') && (cpio_header[5] != '2')) { |
| + | if ((strncmp(&cpio_header[0], "07070", 5) != 0) || ((cpio_header[5] != '1') && (cpio_header[5] != '2'))) { |
| bb_error_msg_and_die("Unsupported cpio format, use newc or crc"); | |
| } | |
| @@ -154,36 +143,13 @@ extern char get_header_cpio(archive_handle_t *archive_handle) | |
| } | |
| file_header->device = (major << 8) | minor; | |
| - | extract_flag = FALSE; |
| if (archive_handle->filter(archive_handle) == EXIT_SUCCESS) { | |
| - | struct stat statbuf; |
| - | |
| - | extract_flag = TRUE; |
| - | |
| - | /* Check if the file already exists */ |
| - | if (lstat (file_header->name, &statbuf) == 0) { |
| - | if ((archive_handle->flags & ARCHIVE_EXTRACT_UNCONDITIONAL) || (statbuf.st_mtime < file_header->mtime)) { |
| - | /* Remove file if flag set or its older than the file to be extracted */ |
| - | if (unlink(file_header->name) == -1) { |
| - | bb_perror_msg_and_die("Couldnt remove old file"); |
| - | } |
| - | } else { |
| - | if (! archive_handle->flags & ARCHIVE_EXTRACT_QUIET) { |
| - | bb_error_msg("%s not created: newer or same age file exists", file_header->name); |
| - | } |
| - | extract_flag = FALSE; |
| - | } |
| - | } |
| - | archive_handle->action_header(file_header); |
| - | } |
| - | |
| - | archive_handle->action_header(file_header); |
| - | if (extract_flag) { |
| archive_handle->action_data(archive_handle); | |
| + | archive_handle->action_header(archive_handle->file_header); |
| } else { | |
| - | data_skip(archive_handle); |
| + | data_skip(archive_handle); |
| } | |
| + | |
| archive_handle->offset += file_header->size; | |
| return (EXIT_SUCCESS); | |
| } | |
| - | |
| @@ -5,6 +5,7 @@ | |
| #define ARCHIVE_CREATE_LEADING_DIRS 2 | |
| #define ARCHIVE_EXTRACT_UNCONDITIONAL 4 | |
| #define ARCHIVE_EXTRACT_QUIET 8 | |
| + | #define ARCHIVE_EXTRACT_NEWER 16 |
| #include <sys/types.h> | |
| #include <stdio.h> | |