diff options
-rw-r--r-- | libarchive_fe/line_reader.c | 22 | ||||
-rw-r--r-- | libarchive_fe/line_reader.h | 2 | ||||
-rw-r--r-- | libarchive_fe/matching.c | 5 | ||||
-rw-r--r-- | libarchive_fe/matching.h | 2 | ||||
-rw-r--r-- | tar/read.c | 3 | ||||
-rw-r--r-- | tar/test/test_option_T_upper.c | 27 | ||||
-rw-r--r-- | tar/write.c | 2 |
7 files changed, 44 insertions, 19 deletions
diff --git a/libarchive_fe/line_reader.c b/libarchive_fe/line_reader.c index 52757638..21e1c705 100644 --- a/libarchive_fe/line_reader.c +++ b/libarchive_fe/line_reader.c @@ -51,12 +51,12 @@ struct lafe_line_reader { char *buff, *buff_end, *line_start, *line_end, *p; char *pathname; size_t buff_length; - int separator; + int nullSeparator; /* Lines separated by null, not CR/CRLF/etc. */ int ret; }; struct lafe_line_reader * -lafe_line_reader(const char *pathname, char separator) +lafe_line_reader(const char *pathname, int nullSeparator) { struct lafe_line_reader *lr; @@ -64,7 +64,7 @@ lafe_line_reader(const char *pathname, char separator) if (lr == NULL) lafe_errc(1, ENOMEM, "Can't open %s", pathname); - lr->separator = separator; + lr->nullSeparator = nullSeparator; lr->pathname = strdup(pathname); if (strcmp(pathname, "-") == 0) @@ -91,14 +91,22 @@ lafe_line_reader_next(struct lafe_line_reader *lr) for (;;) { /* If there's a line in the buffer, return it immediately. */ while (lr->line_end < lr->buff_end) { - if (*lr->line_end == lr->separator) { + if (lr->nullSeparator) { + if (*lr->line_end == '\0') { + line_start = lr->line_start; + lr->line_start = lr->line_end + 1; + lr->line_end = lr->line_start; + return (line_start); + } + } else if (*lr->line_end == '\x0a' || *lr->line_end == '\x0d') { *lr->line_end = '\0'; line_start = lr->line_start; lr->line_start = lr->line_end + 1; lr->line_end = lr->line_start; - return (line_start); - } else - lr->line_end++; + if (line_start[0] != '\0') + return (line_start); + } + lr->line_end++; } /* If we're at end-of-file, process the final data. */ diff --git a/libarchive_fe/line_reader.h b/libarchive_fe/line_reader.h index 7bb1742c..d092c051 100644 --- a/libarchive_fe/line_reader.h +++ b/libarchive_fe/line_reader.h @@ -28,7 +28,7 @@ struct lafe_line_reader; -struct lafe_line_reader *lafe_line_reader(const char *, char separator); +struct lafe_line_reader *lafe_line_reader(const char *, int nullSeparator); const char *lafe_line_reader_next(struct lafe_line_reader *); void lafe_line_reader_free(struct lafe_line_reader *); diff --git a/libarchive_fe/matching.c b/libarchive_fe/matching.c index af5bde4e..bdfd07b7 100644 --- a/libarchive_fe/matching.c +++ b/libarchive_fe/matching.c @@ -111,13 +111,14 @@ lafe_include(struct lafe_matching **matching, const char *pattern) } int -lafe_include_from_file(struct lafe_matching **matching, const char *pathname) +lafe_include_from_file(struct lafe_matching **matching, const char *pathname, + int nullSeparator) { struct lafe_line_reader *lr; const char *p; int ret = 0; - lr = lafe_line_reader(pathname, '\n'); + lr = lafe_line_reader(pathname, nullSeparator); while ((p = lafe_line_reader_next(lr)) != NULL) { if (lafe_include(matching, p) != 0) ret = -1; diff --git a/libarchive_fe/matching.h b/libarchive_fe/matching.h index 5cdc0166..f4edebd4 100644 --- a/libarchive_fe/matching.h +++ b/libarchive_fe/matching.h @@ -36,7 +36,7 @@ int lafe_exclude_from_file(struct lafe_matching **matching, const char *pathname); int lafe_include(struct lafe_matching **matching, const char *pattern); int lafe_include_from_file(struct lafe_matching **matching, - const char *pathname); + const char *pathname, int nullSeparator); int lafe_excluded(struct lafe_matching *, const char *pathname); void lafe_cleanup_exclusions(struct lafe_matching **); @@ -142,7 +142,8 @@ read_archive(struct bsdtar *bsdtar, char mode) } if (bsdtar->names_from_file != NULL) - lafe_include_from_file(&bsdtar->matching, bsdtar->names_from_file); + lafe_include_from_file(&bsdtar->matching, + bsdtar->names_from_file, bsdtar->option_null); a = archive_read_new(); if (bsdtar->compress_program != NULL) diff --git a/tar/test/test_option_T_upper.c b/tar/test/test_option_T_upper.c index 4e656afc..fbb83d72 100644 --- a/tar/test/test_option_T_upper.c +++ b/tar/test/test_option_T_upper.c @@ -51,27 +51,35 @@ DEFINE_TEST(test_option_T_upper) if (!touch("d1/d2/f3")) return; if (!touch("d1/d2/f4")) return; if (!touch("d1/d2/f5")) return; + if (!touch("d1/d2/f6")) return; + if (!touch("d1/d2/f\x0a")) return; /* Populate a file list */ f = fopen("filelist", "w+"); if (!assert(f != NULL)) return; - fprintf(f, "d1/f1\n"); - fprintf(f, "d1/d2/f4\n"); + /* Use a variety of text line endings. */ + fprintf(f, "d1/f1\x0d\x0a"); /* CRLF */ + fprintf(f, "d1/d2/f4\x0a"); /* NL */ + fprintf(f, "d1/d2/f6"); /* EOF */ fclose(f); /* Populate a second file list */ f = fopen("filelist2", "w+"); if (!assert(f != NULL)) return; - fprintf(f, "d1/d2/f3\n"); - fprintf(f, "d1/d2/f5\n"); + /* Use null-terminated names. */ + fprintf(f, "d1/d2/f3"); + fwrite("\0", 1, 1, f); + fprintf(f, "d1/d2/f5"); + fwrite("\0", 1, 1, f); + fprintf(f, "d1/d2/f\x0a"); + fwrite("\0", 1, 1, f); fclose(f); /* Use -c -T to archive up the files. */ r = systemf("%s -c -f test1.tar -T filelist > test1.out 2> test1.err", testprog); - failure("Failure here probably means that tar can't archive zero-length files without reading them"); assert(r == 0); assertEmptyFile("test1.out"); assertEmptyFile("test1.err"); @@ -89,9 +97,11 @@ DEFINE_TEST(test_option_T_upper) assertFileNotExists("test1/d1/d2/f3"); assertFileExists("test1/d1/d2/f4"); assertFileNotExists("test1/d1/d2/f5"); + assertFileExists("test1/d1/d2/f6"); + assertFileNotExists("test1/d1/d2/f\x0a"); /* Use -r -T to add more files to the archive. */ - systemf("%s -r -f test1.tar -T filelist2 > test2.out 2> test2.err", + systemf("%s -r -f test1.tar --null -T filelist2 > test2.out 2> test2.err", testprog); assertEmptyFile("test2.out"); assertEmptyFile("test2.err"); @@ -108,6 +118,8 @@ DEFINE_TEST(test_option_T_upper) assertFileExists("test3/d1/d2/f3"); assertFileExists("test3/d1/d2/f4"); assertFileExists("test3/d1/d2/f5"); + assertFileExists("test3/d1/d2/f6"); + assertFileExists("test3/d1/d2/f\x0a"); /* Use -x -T to dearchive the files (verify -x -T together) */ if (!assertMakeDir("test2", 0755)) return; @@ -121,6 +133,8 @@ DEFINE_TEST(test_option_T_upper) assertFileNotExists("test2/d1/d2/f3"); assertFileExists("test2/d1/d2/f4"); assertFileNotExists("test2/d1/d2/f5"); + assertFileExists("test2/d1/d2/f6"); + assertFileNotExists("test2/d1/d2/f\x0a"); assertMakeDir("test4", 0755); assertMakeDir("test4_out", 0755); @@ -148,6 +162,7 @@ DEFINE_TEST(test_option_T_upper) } else { skipping("bsdtar does not support -s option on this platform"); } + /* TODO: Include some use of -C directory-changing within the filelist. */ /* I'm pretty sure -C within the filelist is broken on extract. */ } diff --git a/tar/write.c b/tar/write.c index 47ded8f2..c25a9af2 100644 --- a/tar/write.c +++ b/tar/write.c @@ -520,7 +520,7 @@ archive_names_from_file(struct bsdtar *bsdtar, struct archive *a) bsdtar->next_line_is_dir = 0; - lr = lafe_line_reader(bsdtar->names_from_file, '\n'); + lr = lafe_line_reader(bsdtar->names_from_file, bsdtar->option_null); while ((line = lafe_line_reader_next(lr)) != NULL) { if (bsdtar->next_line_is_dir) { set_chdir(bsdtar, line); |