diff options
author | Joerg Wunsch <joerg@FreeBSD.org> | 1996-03-18 23:08:29 +0000 |
---|---|---|
committer | Joerg Wunsch <joerg@FreeBSD.org> | 1996-03-18 23:08:29 +0000 |
commit | ff910f350764cd35e40206856c38ebd4c380d3b2 (patch) | |
tree | 4bb9ebb133018741a19fd59ad93a0f2067bd6912 /gnu/usr.bin/cpio | |
parent | 61e269f90bb4c115684103687c335d5dbffd3632 (diff) | |
download | src-ff910f350764cd35e40206856c38ebd4c380d3b2.tar.gz src-ff910f350764cd35e40206856c38ebd4c380d3b2.zip |
Fix an infinite loop for empty files in the archive, and handle
sparsely stored linked files correctly.
Submitted by: haug@conterra.com (Brian R. Haug)
Notes
Notes:
svn path=/head/; revision=14684
Diffstat (limited to 'gnu/usr.bin/cpio')
-rw-r--r-- | gnu/usr.bin/cpio/copyin.c | 37 |
1 files changed, 34 insertions, 3 deletions
diff --git a/gnu/usr.bin/cpio/copyin.c b/gnu/usr.bin/cpio/copyin.c index 7c5d349db042..e8804de4ea1d 100644 --- a/gnu/usr.bin/cpio/copyin.c +++ b/gnu/usr.bin/cpio/copyin.c @@ -38,6 +38,7 @@ static void skip_padding (); static void defer_copyin (); static void create_defered_links (); static void create_final_defers (); +static int check_for_deferments (); /* Return 16-bit integer I with the bytes swapped. */ #define swab_short(i) ((((i) << 8) & 0xff00) | (((i) >> 8) & 0x00ff)) @@ -381,6 +382,7 @@ process_copy_in () int out_file_des; /* Output file descriptor. */ int in_file_des; /* Input file descriptor. */ char skip_file; /* Flag for use with patterns. */ + char deferred; /* Deferred file creation, don't print name. */ int existing_dir; /* True if file is a dir & already exists. */ int i; /* Loop index variable. */ char *link_name = NULL; /* Name of hard and symbolic links. */ @@ -472,6 +474,7 @@ process_copy_in () break; } + deferred = FALSE; /* Does the file name match one of the given patterns? */ if (num_patterns <= 0) skip_file = FALSE; @@ -484,6 +487,11 @@ process_copy_in () if (fnmatch (save_patterns[i], file_hdr.c_name, 0) == 0) skip_file = !copy_matching_files; } + if (skip_file) { + skip_file = check_for_deferments(&file_hdr); + if (!skip_file) + deferred = TRUE; /* don't print this name */ + } } if (skip_file) @@ -921,9 +929,9 @@ process_copy_in () skip_padding (in_file_des, file_hdr.c_filesize); } - if (verbose_flag) + if (verbose_flag && !deferred) fprintf (stderr, "%s\n", file_hdr.c_name); - if (dot_flag) + if (dot_flag && !deferred) fputc ('.', stderr); } } @@ -1226,7 +1234,6 @@ create_final_defers () for (d = deferments; d != NULL; d = d->next) { - d = deferments; link_res = link_to_maj_min_ino (d->header.c_name, d->header.c_dev_maj, d->header.c_dev_maj, d->header.c_ino); @@ -1270,3 +1277,27 @@ create_final_defers () } } } + +static int +check_for_deferments(struct new_cpio_header *file_hdr) +{ + struct deferment *d; + struct deferment *prev = NULL; + + for (d = deferments; d != NULL; d = d->next) { + if (file_hdr->c_ino == d->header.c_ino && + file_hdr->c_dev_maj == d->header.c_dev_maj && + file_hdr->c_dev_min == d->header.c_dev_min) { + free(file_hdr->c_name); + if (prev != NULL) + prev->next = d->next; + else + deferments = d->next; + file_hdr->c_name = strdup(d->header.c_name); + free_deferment(d); + return FALSE; + } + prev = d; + } + return TRUE; +} |