]> git.ipfire.org Git - thirdparty/libarchive.git/commitdiff
IFC
authorTim Kientzle <kientzle@gmail.com>
Sat, 23 Aug 2008 23:37:23 +0000 (19:37 -0400)
committerTim Kientzle <kientzle@gmail.com>
Sat, 23 Aug 2008 23:37:23 +0000 (19:37 -0400)
SVN-Revision: 184

22 files changed:
cpio/cpio.c
cpio/test/Makefile
cpio/test/main.c
cpio/test/test_basic.c
cpio/test/test_format_newc.c
cpio/test/test_gcpio_compat.c
cpio/test/test_option_a.c
cpio/test/test_passthrough_dotdot.c [new file with mode: 0644]
cpio/test/test_passthrough_reverse.c [new file with mode: 0644]
libarchive/archive_write_disk.c
tar/Makefile
tar/bsdtar.c
tar/read.c
tar/test/Makefile
tar/test/main.c
tar/test/test.h
tar/test/test_option_q.c [new file with mode: 0644]
tar/test/test_patterns.c
tar/test/test_patterns.tgz.err.uu [deleted file]
tar/test/test_patterns.tgz.out.uu [deleted file]
tar/test/test_patterns_2.tgz.uu [moved from tar/test/test_patterns.tgz.uu with 68% similarity]
tar/test/test_patterns_3.tgz.uu [new file with mode: 0644]

index ee932c975e5b5ce4c5fb34a70abaab0685752dab..607dfb78ca92b92df9f4c127444d831ec5a07ca3 100644 (file)
@@ -26,7 +26,7 @@
 
 
 #include "cpio_platform.h"
-__FBSDID("$FreeBSD: src/usr.bin/cpio/cpio.c,v 1.10 2008/07/30 03:35:45 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/cpio/cpio.c,v 1.11 2008/08/20 16:39:18 kientzle Exp $");
 
 #include <sys/types.h>
 #include <archive.h>
@@ -112,6 +112,8 @@ main(int argc, char *argv[])
        cpio->extract_flags |= ARCHIVE_EXTRACT_SECURE_SYMLINKS;
        cpio->extract_flags |= ARCHIVE_EXTRACT_SECURE_NODOTDOT;
        cpio->extract_flags |= ARCHIVE_EXTRACT_PERM;
+       cpio->extract_flags |= ARCHIVE_EXTRACT_FFLAGS;
+       cpio->extract_flags |= ARCHIVE_EXTRACT_ACL;
        if (geteuid() == 0)
                cpio->extract_flags |= ARCHIVE_EXTRACT_OWNER;
        cpio->bytes_per_block = 512;
index 9ba06a6b8a6094201d1f9b6d563609d0be034f77..c19e56670437ad694efd95a9a13c5182a928912f 100644 (file)
@@ -1,4 +1,4 @@
-# $FreeBSD: src/lib/libarchive/test/Makefile,v 1.11 2007/07/13 15:14:35 kientzle Exp $
+# $FreeBSD: src/usr.bin/cpio/test/Makefile,v 1.3 2008/08/24 05:14:03 kientzle Exp $
 
 # Where to find the cpio sources (for the internal unit tests)
 CPIO_SRCDIR=${.CURDIR}/..
@@ -27,7 +27,9 @@ TESTS=        \
        test_option_y.c                         \
        test_option_z.c                         \
        test_owner_parse.c                      \
-       test_pathmatch.c                        \
+       test_passthrough_dotdot.c               \
+       test_passthrough_reverse.c              \
+       test_pathmatch.c
 
 # Build the test program
 SRCS= list.h                                   \
index e0f8c2e1175ab37fb19dde71c14f14d50c117cc6..379968b1e1b525fe760743b2c2011eb91ed8ae18 100644 (file)
@@ -44,7 +44,7 @@
 #undef EXTRA_DUMP           /* How to dump extra data */
 /* How to generate extra version info. */
 #define        EXTRA_VERSION    (systemf("%s --version", testprog) ? "" : "")
-__FBSDID("$FreeBSD: src/usr.bin/cpio/test/main.c,v 1.2 2008/06/21 02:17:18 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/main.c,v 1.3 2008/08/24 04:58:22 kientzle Exp $");
 
 /*
  * "list.h" is simply created by "grep DEFINE_TEST"; it has
@@ -598,8 +598,8 @@ test_assert_file_contents(const void *buff, int s, const char *fpattern, ...)
        va_end(ap);
 
        fd = open(f, O_RDONLY);
-       contents = malloc(s * 2);
-       n = read(fd, contents, s * 2);
+       contents = malloc(s * 2 + 128);
+       n = read(fd, contents, s * 2 + 128);
        if (n == s && memcmp(buff, contents, s) == 0) {
                free(contents);
                return (1);
index 6ea0c5d6dac6b78326e7161ac4a8115b2094e577..954153e280472d158825152a7d5cba93dbe080d9 100644 (file)
@@ -23,7 +23,7 @@
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 #include "test.h"
-__FBSDID("$FreeBSD$");
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_basic.c,v 1.2 2008/08/22 02:27:06 kientzle Exp $");
 
 static void
 verify_files(const char *target)
@@ -155,7 +155,7 @@ passthrough(const char *target)
        /*
         * Use cpio passthrough mode to copy files to another directory.
         */
-       r = systemf("%s -p -W quiet %s <filelist >%s/stdout 2>%s/stderr",
+       r = systemf("%s -p %s <filelist >%s/stdout 2>%s/stderr",
            testprog, target, target, target);
        failure("Error invoking %s -p", testprog);
        assertEqualInt(r, 0);
@@ -165,7 +165,10 @@ passthrough(const char *target)
        /* Verify stderr. */
        failure("Error invoking %s -p in dir %s",
            testprog, target);
-       assertEmptyFile("stderr");
+       /* gcpio 2.9 writes "1 block" to stderr */
+       /* assertFileContents("1 block\n", 8, "stderr"); */
+       /* bsdcpio writes nothing to stderr for passthrough mode */
+       assertFileContents("", 0, "stderr");
 
        verify_files(target);
        chdir("..");
@@ -218,8 +221,10 @@ DEFINE_TEST(test_basic)
        basic_cpio("copy", "", "", "2 blocks\n");
        basic_cpio("copy_odc", "--format=odc", "", "2 blocks\n");
        basic_cpio("copy_newc", "-H newc", "", "2 blocks\n");
-       basic_cpio("copy_cpio", "-H odc", "", "2 blocks\n");
-       basic_cpio("copy_ustar", "-H ustar", "", "9 blocks\n");
+       basic_cpio("copy_cpio", "-H odc", "", "1 block\n");
+       /* For some reason, gcpio 2.9 writes 7 blocks but only reads 6? */
+       /* bsdcpio writes 7 blocks and reads 7 blocks. */
+       basic_cpio("copy_ustar", "-H ustar", "", "7 blocks\n");
        /* Copy in one step using -p */
        passthrough("passthrough");
 
index 0714bd427e2194875745156b1e02754729aa83cf..5bae145cd0ac1732a16a48a6d04d39beeaedd3dc 100644 (file)
@@ -23,7 +23,7 @@
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 #include "test.h"
-__FBSDID("$FreeBSD$");
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_format_newc.c,v 1.2 2008/08/22 02:09:10 kientzle Exp $");
 
 static int
 is_hex(const char *p, size_t l)
@@ -68,7 +68,7 @@ DEFINE_TEST(test_format_newc)
        int devmajor, devminor, ino, gid;
        time_t t, t2, now;
        char *p, *e;
-       size_t s;
+       size_t s, fs, ns;
        mode_t oldmask;
 
        oldmask = umask(0);
@@ -141,16 +141,21 @@ DEFINE_TEST(test_format_newc)
            "       first appearance should be empty, so this file size\n"
            "       field should be zero");
        assertEqualInt(0, from_hex(e + 54, 8)); /* File size */
+       fs = from_hex(e + 54, 8);
+       fs += 3 & -fs;
        devmajor = from_hex(e + 62, 8); /* devmajor */
        devminor = from_hex(e + 70, 8); /* devminor */
        assert(is_hex(e + 78, 8)); /* rdevmajor */
        assert(is_hex(e + 86, 8)); /* rdevminor */
        assertEqualMem(e + 94, "00000006", 8); /* Name size */
+       ns = from_hex(e + 94, 8);
+       ns += 3 & (-ns - 2);
        assertEqualInt(0, from_hex(e + 102, 8)); /* check field */
        assertEqualMem(e + 110, "file1\0", 6); /* Name contents */
        /* Since there's another link, no file contents here. */
        /* But add in file size so that an error here doesn't cascade. */
-       e += 116 + from_hex(e + 54, 8) + (3 & -from_hex(e + 54, 8));
+       e += 110 + fs + ns;
+
        /* "symlink" pointing to "file1" */
        assert(is_hex(e, 110));
        assertEqualMem(e + 0, "070701", 6); /* Magic */
@@ -163,15 +168,19 @@ DEFINE_TEST(test_format_newc)
        failure("First entry created at t=0x%08x this entry created at t2=0x%08x", t, t2);
        assert(t2 == t || t2 == t + 1); /* Almost same as first entry. */
        assertEqualMem(e + 54, "00000005", 8); /* File size */
+       fs = from_hex(e + 54, 8);
+       fs += 3 & -fs;
        assertEqualInt(devmajor, from_hex(e + 62, 8)); /* devmajor */
        assertEqualInt(devminor, from_hex(e + 70, 8)); /* devminor */
        assert(is_hex(e + 78, 8)); /* rdevmajor */
        assert(is_hex(e + 86, 8)); /* rdevminor */
        assertEqualMem(e + 94, "00000008", 8); /* Name size */
+       ns = from_hex(e + 94, 8);
+       ns += 3 & (-ns - 2);
        assertEqualInt(0, from_hex(e + 102, 8)); /* check field */
        assertEqualMem(e + 110, "symlink\0\0\0", 10); /* Name contents */
-       assertEqualMem(e + 120, "file1\0\0\0", 8); /* symlink target */
-       e += 120 + from_hex(e + 54, 8) + (3 & -from_hex(e + 54, 8));
+       assertEqualMem(e + 110 + ns, "file1\0\0\0", 8); /* symlink target */
+       e += 110 + fs + ns;
 
        /* "dir" */
        assert(is_hex(e, 110));
@@ -185,16 +194,18 @@ DEFINE_TEST(test_format_newc)
        failure("First entry created at t=0x%08x this entry created at t2=0x%08x", t, t2);
        assert(t2 == t || t2 == t + 1); /* Almost same as first entry. */
        assertEqualMem(e + 54, "00000000", 8); /* File size */
+       fs = from_hex(e + 54, 8);
+       fs += 3 & -fs;
        assertEqualInt(devmajor, from_hex(e + 62, 8)); /* devmajor */
        assertEqualInt(devminor, from_hex(e + 70, 8)); /* devminor */
        assert(is_hex(e + 78, 8)); /* rdevmajor */
        assert(is_hex(e + 86, 8)); /* rdevminor */
        assertEqualMem(e + 94, "00000004", 8); /* Name size */
+       ns = from_hex(e + 94, 8);
+       ns += 3 & (-ns - 2);
        assertEqualInt(0, from_hex(e + 102, 8)); /* check field */
        assertEqualMem(e + 110, "dir\0\0\0", 6); /* Name contents */
-       e += 116;
-
-       /* TODO: Verify other types of entries. */
+       e += 110 + fs + ns;
 
        /* Hardlink identical to "file1" */
        /* Since we only wrote two of the three links to this
@@ -211,15 +222,19 @@ DEFINE_TEST(test_format_newc)
        failure("First entry created at t=0x%08x this entry created at t2=0x%08x", t, t2);
        assert(t2 == t || t2 == t + 1); /* Almost same as first entry. */
        assertEqualInt(10, from_hex(e + 54, 8)); /* File size */
+       fs = from_hex(e + 54, 8);
+       fs += 3 & -fs;
        assertEqualInt(devmajor, from_hex(e + 62, 8)); /* devmajor */
        assertEqualInt(devminor, from_hex(e + 70, 8)); /* devminor */
        assert(is_hex(e + 78, 8)); /* rdevmajor */
        assert(is_hex(e + 86, 8)); /* rdevminor */
        assertEqualMem(e + 94, "00000009", 8); /* Name size */
+       ns = from_hex(e + 94, 8);
+       ns += 3 & (-ns - 2);
        assertEqualInt(0, from_hex(e + 102, 8)); /* check field */
        assertEqualMem(e + 110, "hardlink\0\0", 10); /* Name contents */
-       assertEqualMem(e + 120, "123456789\0\0\0", 12); /* File contents */
-       e += 120 + from_hex(e + 54, 8) + (3 & -from_hex(e + 54, 8));
+       assertEqualMem(e + 110 + ns, "123456789\0\0\0", 12); /* File contents */
+       e += 110 + ns + fs;
 
        /* Last entry is end-of-archive marker. */
        assert(is_hex(e, 110));
index 4c69abb63687e71198a13a5598986e75ac84c097..42ea9e1bbd13ca63c882755a729f14d63759a6c1 100644 (file)
@@ -23,8 +23,7 @@
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 #include "test.h"
-__FBSDID("$FreeBSD$");
-
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_gcpio_compat.c,v 1.2 2008/08/22 02:27:06 kientzle Exp $");
 
 static void
 unpack_test(const char *from, const char *options, const char *se)
@@ -48,6 +47,7 @@ unpack_test(const char *from, const char *options, const char *se)
        assertEqualInt(r, 0);
 
        /* Verify that nothing went to stderr. */
+       failure("Error invoking %s -i %s < %s", testprog, options, from);
        assertFileContents(se, strlen(se), "unpack.err");
 
        /*
@@ -121,6 +121,7 @@ DEFINE_TEST(test_gcpio_compat)
        unpack_test("test_gcpio_compat_ref.bin", "", "1 block\n");
        unpack_test("test_gcpio_compat_ref.crc", "", "2 blocks\n");
        unpack_test("test_gcpio_compat_ref.newc", "", "2 blocks\n");
+       /* gcpio-2.9 only reads 6 blocks here */
        unpack_test("test_gcpio_compat_ref.ustar", "", "7 blocks\n");
 
        umask(oldumask);
index c063280f7d720393b4200bf4713bbfe53537857e..f735b9116e06d107a0ced4a27165155cac42a20d 100644 (file)
@@ -24,7 +24,7 @@
  */
 #include "test.h"
 #include <utime.h>
-__FBSDID("$FreeBSD$");
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_option_a.c,v 1.2 2008/08/22 02:27:06 kientzle Exp $");
 
 static struct {
        const char *name;
@@ -118,6 +118,7 @@ DEFINE_TEST(test_option_a)
                /* Copy the file without -a; should change the atime. */
                r = systemf("echo %s | %s -pd copy-no-a > copy-no-a.out 2>copy-no-a.err", files[1].name, testprog);
                assertEqualInt(r, 0);
+               /* bsdcpio writes nothing to stderr in -p mode */
                assertEmptyFile("copy-no-a.err");
                assertEmptyFile("copy-no-a.out");
                assertEqualInt(0, stat(files[1].name, &st));
diff --git a/cpio/test/test_passthrough_dotdot.c b/cpio/test/test_passthrough_dotdot.c
new file mode 100644 (file)
index 0000000..e9d5c61
--- /dev/null
@@ -0,0 +1,89 @@
+/*-
+ * Copyright (c) 2003-2007 Tim Kientzle
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#include "test.h"
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_passthrough_dotdot.c,v 1.2 2008/08/24 05:24:52 kientzle Exp $");
+
+/*
+ * Verify that "cpio -p .." works.
+ */
+
+DEFINE_TEST(test_passthrough_dotdot)
+{
+       struct stat st;
+       int fd, r;
+       int filelist;
+       int oldumask;
+
+       oldumask = umask(0);
+
+       /*
+        * Create an assortment of files on disk.
+        */
+       filelist = open("filelist", O_CREAT | O_WRONLY, 0644);
+
+       /* Directory. */
+       assertEqualInt(0, mkdir("dir", 0755));
+       assertEqualInt(0, chdir("dir"));
+
+       write(filelist, ".\n", 2);
+
+       /* File with 10 bytes content. */
+       fd = open("file", O_CREAT | O_WRONLY, 0642);
+       assert(fd >= 0);
+       assertEqualInt(10, write(fd, "123456789", 10));
+       close(fd);
+       write(filelist, "file\n", 5);
+
+       /* All done. */
+       close(filelist);
+
+
+       /*
+        * Use cpio passthrough mode to copy files to another directory.
+        */
+       r = systemf("%s -pdvm .. <../filelist >../stdout 2>../stderr",
+           testprog);
+       failure("Error invoking %s -pd ..", testprog);
+       assertEqualInt(r, 0);
+
+       assertEqualInt(0, chdir(".."));
+
+       /* Verify stderr and stdout. */
+       assertFileContents("../file\n", 8, "stderr");
+       assertEmptyFile("stdout");
+
+       /* Regular file. */
+       r = lstat("file", &st);
+       failure("Failed to stat file, errno=%d", errno);
+       assertEqualInt(r, 0);
+       if (r == 0) {
+               assert(S_ISREG(st.st_mode));
+               assertEqualInt(0642, st.st_mode & 0777);
+               assertEqualInt(10, st.st_size);
+               assertEqualInt(1, st.st_nlink);
+       }
+
+       umask(oldumask);
+}
diff --git a/cpio/test/test_passthrough_reverse.c b/cpio/test/test_passthrough_reverse.c
new file mode 100644 (file)
index 0000000..00ee2bc
--- /dev/null
@@ -0,0 +1,103 @@
+/*-
+ * Copyright (c) 2003-2007 Tim Kientzle
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#include "test.h"
+__FBSDID("$FreeBSD: src/usr.bin/cpio/test/test_passthrough_reverse.c,v 1.1 2008/08/24 04:58:22 kientzle Exp $");
+
+/*
+ * As reported by Bernd Walter:  Some people are in the habit of
+ * using "find -d" to generate a list for cpio -p because that
+ * copies the top-level dir last, which preserves owner and mode
+ * information.  That's not necessary for bsdcpio (libarchive defers
+ * restoring directory information), but bsdcpio should still generate
+ * the correct results with this usage.
+ */
+
+DEFINE_TEST(test_passthrough_reverse)
+{
+       struct stat st;
+       int fd, r;
+       int filelist;
+       int oldumask;
+
+       oldumask = umask(0);
+
+       /*
+        * Create an assortment of files on disk.
+        */
+       filelist = open("filelist", O_CREAT | O_WRONLY, 0644);
+
+       /* Directory. */
+       assertEqualInt(0, mkdir("dir", 0743));
+
+       /* File with 10 bytes content. */
+       fd = open("dir/file", O_CREAT | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(10, write(fd, "123456789", 10));
+       close(fd);
+       write(filelist, "dir/file\n", 9);
+
+       /* Write dir last. */
+       write(filelist, "dir\n", 4);
+
+       /* All done. */
+       close(filelist);
+
+
+       /*
+        * Use cpio passthrough mode to copy files to another directory.
+        */
+       r = systemf("%s -pdvm out <filelist >stdout 2>stderr", testprog);
+       failure("Error invoking %s -pd out", testprog);
+       assertEqualInt(r, 0);
+
+       assertEqualInt(0, chdir("out"));
+
+       /* Verify stderr and stdout. */
+       assertFileContents("out/dir/file\nout/dir\n", 21, "../stderr");
+       assertEmptyFile("../stdout");
+
+       /* dir */
+       r = lstat("dir", &st);
+       if (r == 0) {
+               assertEqualInt(r, 0);
+               assert(S_ISDIR(st.st_mode));
+               failure("st.st_mode=0%o",  st.st_mode);
+               assertEqualInt(0743, st.st_mode & 0777);
+       }
+
+
+       /* Regular file. */
+       r = lstat("dir/file", &st);
+       failure("Failed to stat dir/file, errno=%d", errno);
+       assertEqualInt(r, 0);
+       if (r == 0) {
+               assert(S_ISREG(st.st_mode));
+               assertEqualInt(0644, st.st_mode & 0777);
+               assertEqualInt(10, st.st_size);
+               assertEqualInt(1, st.st_nlink);
+       }
+
+       umask(oldumask);
+}
index 44e721eb8b4e3c14cf667392f736baafe828dd57..d0b3a2cec45814891f2dbc5e69d81f6ea96c7e5c 100644 (file)
@@ -25,7 +25,7 @@
  */
 
 #include "archive_platform.h"
-__FBSDID("$FreeBSD: src/lib/libarchive/archive_write_disk.c,v 1.28 2008/07/05 01:48:33 kientzle Exp $");
+__FBSDID("$FreeBSD: src/lib/libarchive/archive_write_disk.c,v 1.29 2008/08/24 05:01:01 kientzle Exp $");
 
 #ifdef HAVE_SYS_TYPES_H
 #include <sys/types.h>
@@ -906,7 +906,11 @@ restore_entry(struct archive_write_disk *a)
 
                /* TODO: if it's a symlink... */
 
-               if (a->flags & ARCHIVE_EXTRACT_NO_OVERWRITE_NEWER) {
+               /*
+                * NO_OVERWRITE_NEWER doesn't apply to directories.
+                */
+               if ((a->flags & ARCHIVE_EXTRACT_NO_OVERWRITE_NEWER)
+                   &&  !S_ISDIR(a->st.st_mode)) {
                        if (!older(&(a->st), a->entry)) {
                                archive_set_error(&a->archive, 0,
                                    "File on disk is not older; skipping.");
index fa72cfbd11c44566310a5f1f47bd3f683603eda9..67f2b04743353649815b47fc22130ede4a0f7939 100644 (file)
@@ -1,4 +1,4 @@
-# $FreeBSD: src/usr.bin/tar/Makefile,v 1.37 2008/07/05 02:09:54 kientzle Exp $
+# $FreeBSD: src/usr.bin/tar/Makefile,v 1.38 2008/08/22 01:31:13 kientzle Exp $
 
 PROG=  bsdtar
 BSDTAR_VERSION_STRING=2.5.5
@@ -14,6 +14,6 @@ MLINKS=       bsdtar.1 tar.1
 
 .PHONY: check test
 check test: $(PROG) bsdtar.1.gz
-       cd ${.CURDIR}/test && make clean test
+       cd ${.CURDIR}/test && make test
 
 .include <bsd.prog.mk>
index 1c13cc6bfbe76ffd055f70ebdb72e592aface94d..40ddd78a451e9b53f49385e754680a762394850c 100644 (file)
@@ -24,7 +24,7 @@
  */
 
 #include "bsdtar_platform.h"
-__FBSDID("$FreeBSD: src/usr.bin/tar/bsdtar.c,v 1.91 2008/05/26 17:10:10 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/tar/bsdtar.c,v 1.92 2008/08/22 01:22:55 kientzle Exp $");
 
 #ifdef HAVE_SYS_PARAM_H
 #include <sys/param.h>
@@ -118,7 +118,7 @@ static void          version(void);
  * non-option.  Otherwise, GNU getopt() permutes the arguments and
  * screws up -C processing.
  */
-static const char *tar_opts = "+Bb:C:cf:HhI:jkLlmnOoPprts:ST:UuvW:wX:xyZz";
+static const char *tar_opts = "+Bb:C:cf:HhI:jkLlmnOoPpqrts:ST:UuvW:wX:xyZz";
 
 /*
  * Most of these long options are deliberately not documented.  They
index fadd57de828dde977fc9f41ae4e7bd9f07561942..a8cb14ab3c088121268a95a893834f00748aff4a 100644 (file)
@@ -24,7 +24,7 @@
  */
 
 #include "bsdtar_platform.h"
-__FBSDID("$FreeBSD: src/usr.bin/tar/read.c,v 1.39 2008/07/05 02:05:55 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/tar/read.c,v 1.40 2008/08/21 06:41:14 kientzle Exp $");
 
 #ifdef HAVE_SYS_TYPES_H
 #include <sys/types.h>
@@ -210,22 +210,17 @@ read_archive(struct bsdtar *bsdtar, char mode)
                if (excluded(bsdtar, archive_entry_pathname(entry)))
                        continue; /* Excluded by a pattern test. */
 
-               /*
-                * Modify the pathname as requested by the user.  We
-                * do this for -t as well to give users a way to
-                * preview the effects of their rewrites.  We also do
-                * this before extraction security checks (including
-                * leading '/' removal).  Note that some rewrite
-                * failures prevent extraction.
-                */
-               if (edit_pathname(bsdtar, entry))
-                       continue; /* Excluded by a rewrite failure. */
-
                if (mode == 't') {
                        /* Perversely, gtar uses -O to mean "send to stderr"
                         * when used with -t. */
                        out = bsdtar->option_stdout ? stderr : stdout;
 
+                       /*
+                        * TODO: Provide some reasonable way to
+                        * preview rewrites.  gtar always displays
+                        * the unedited path in -t output, which means
+                        * you cannot easily preview rewrites.
+                        */
                        if (bsdtar->verbose < 2)
                                safe_fprintf(out, "%s",
                                    archive_entry_pathname(entry));
@@ -252,6 +247,10 @@ read_archive(struct bsdtar *bsdtar, char mode)
                        }
                        fprintf(out, "\n");
                } else {
+                       /* Note: some rewrite failures prevent extraction. */
+                       if (edit_pathname(bsdtar, entry))
+                               continue; /* Excluded by a rewrite failure. */
+
                        if (bsdtar->option_interactive &&
                            !yes("extract '%s'", archive_entry_pathname(entry)))
                                continue;
index 963110896c7b9b7b648d821eef75338a13335034..079210f2a153e17f8c348c2f64cdbfa942c83703 100644 (file)
@@ -1,4 +1,4 @@
-# $FreeBSD: src/usr.bin/tar/test/Makefile,v 1.2 2008/05/26 17:10:10 kientzle Exp $
+# $FreeBSD: src/usr.bin/tar/test/Makefile,v 1.3 2008/08/22 01:22:55 kientzle Exp $
 
 # Where to find the tar sources (for the internal unit tests)
 TAR_SRCDIR=${.CURDIR}/..
@@ -15,6 +15,7 @@ TESTS=        \
        test_getdate.c                          \
        test_help.c                             \
        test_option_T.c                         \
+       test_option_q.c                         \
        test_patterns.c                         \
        test_stdio.c                            \
        test_version.c
index 27bb48d40944fe0c7ba756fcd724ad9b52252b1a..5549d885c0a564361173202b2b77ed688e12d142 100644 (file)
@@ -44,7 +44,7 @@
 #undef EXTRA_DUMP           /* How to dump extra data */
 /* How to generate extra version info. */
 #define        EXTRA_VERSION    (systemf("%s --version", testprog) ? "" : "")
-__FBSDID("$FreeBSD: src/usr.bin/tar/test/main.c,v 1.3 2008/06/15 10:07:54 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/tar/test/main.c,v 1.4 2008/08/21 07:04:57 kientzle Exp $");
 
 /*
  * "list.h" is simply created by "grep DEFINE_TEST"; it has
@@ -502,6 +502,37 @@ test_assert_empty_file(const char *f1fmt, ...)
        return (0);
 }
 
+int
+test_assert_non_empty_file(const char *f1fmt, ...)
+{
+       char f1[1024];
+       struct stat st;
+       va_list ap;
+
+
+       va_start(ap, f1fmt);
+       vsprintf(f1, f1fmt, ap);
+       va_end(ap);
+
+       if (stat(f1, &st) != 0) {
+               fprintf(stderr, "%s:%d: Could not stat: %s\n",
+                   test_filename, test_line, f1);
+               report_failure(NULL);
+               return (0);
+       }
+       if (st.st_size != 0)
+               return (1);
+
+       failures ++;
+       if (!verbose && previous_failures(test_filename, test_line))
+               return (0);
+
+       fprintf(stderr, "%s:%d: File empty: %s\n",
+           test_filename, test_line, f1);
+       report_failure(NULL);
+       return (0);
+}
+
 /* assertEqualFile() asserts that two files have the same contents. */
 /* TODO: hexdump the first bytes that actually differ. */
 int
index 30321e845d6fce230f4d91e16ef93c434e1b56b3..276c37eb883d2f35612d8c123a82f379c68b0ed1 100644 (file)
@@ -22,7 +22,7 @@
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  *
- * $FreeBSD: src/usr.bin/tar/test/test.h,v 1.3 2008/06/15 10:07:54 kientzle Exp $
+ * $FreeBSD: src/usr.bin/tar/test/test.h,v 1.4 2008/08/21 07:04:57 kientzle Exp $
  */
 
 /* Every test program should #include "test.h" as the first thing. */
@@ -98,6 +98,9 @@
 /* Assert that a file is empty; supports printf-style arguments. */
 #define assertEmptyFile                \
   test_setup(__FILE__, __LINE__);test_assert_empty_file
+/* Assert that a file is not empty; supports printf-style arguments. */
+#define assertNonEmptyFile             \
+  test_setup(__FILE__, __LINE__);test_assert_non_empty_file
 /* Assert that a file exists; supports printf-style arguments. */
 #define assertFileExists               \
   test_setup(__FILE__, __LINE__);test_assert_file_exists
@@ -123,6 +126,7 @@ void test_setup(const char *, int);
 void test_skipping(const char *fmt, ...);
 int test_assert(const char *, int, int, const char *, void *);
 int test_assert_empty_file(const char *, ...);
+int test_assert_non_empty_file(const char *, ...);
 int test_assert_equal_file(const char *, const char *, ...);
 int test_assert_equal_int(const char *, int, int, const char *, int, const char *, void *);
 int test_assert_equal_string(const char *, int, const char *v1, const char *, const char *v2, const char *, void *);
diff --git a/tar/test/test_option_q.c b/tar/test/test_option_q.c
new file mode 100644 (file)
index 0000000..d7011c3
--- /dev/null
@@ -0,0 +1,125 @@
+/*-
+ * Copyright (c) 2003-2007 Tim Kientzle
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR(S) ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#include "test.h"
+__FBSDID("$FreeBSD: src/usr.bin/tar/test/test_option_q.c,v 1.3 2008/08/22 01:35:08 kientzle Exp $");
+
+DEFINE_TEST(test_option_q)
+{
+       int fd;
+
+       /*
+        * Create an archive with several different versions of the
+        * same files.  By default, the last version will overwrite
+        * any earlier versions.  The -q/--fast-read option will
+        * stop early, so we can verify -q/--fast-read by seeing
+        * which version of each file actually ended up being
+        * extracted.  This also exercises -r mode, since that's
+        * what we use to build up the test archive.
+        */
+
+       fd = open("foo", O_CREAT | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(4, write(fd, "foo1", 4));
+       close(fd);
+
+       assertEqualInt(0, systemf("%s -cf archive.tar foo", testprog));
+
+       fd = open("foo", O_TRUNC | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(4, write(fd, "foo2", 4));
+       close(fd);
+
+       assertEqualInt(0, systemf("%s -rf archive.tar foo", testprog));
+
+       fd = open("bar", O_CREAT | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(4, write(fd, "bar1", 4));
+       close(fd);
+
+       assertEqualInt(0, systemf("%s -rf archive.tar bar", testprog));
+
+       fd = open("foo", O_TRUNC | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(4, write(fd, "foo3", 4));
+       close(fd);
+
+       assertEqualInt(0, systemf("%s -rf archive.tar foo", testprog));
+
+       fd = open("bar", O_TRUNC | O_WRONLY, 0644);
+       assert(fd >= 0);
+       assertEqualInt(4, write(fd, "bar2", 4));
+       close(fd);
+
+       assertEqualInt(0, systemf("%s -rf archive.tar bar", testprog));
+
+       /*
+        * Now, try extracting from the test archive with various
+        * combinations of -q.
+        */
+
+       /* Test 1: -q foo should only extract the first foo. */
+       assertEqualInt(0, mkdir("test1", 0755));
+       assertEqualInt(0, chdir("test1"));
+       assertEqualInt(0,
+           systemf("%s -xf ../archive.tar -q foo >test.out 2>test.err",
+               testprog));
+       assertFileContents("foo1", 4, "foo");
+       assertEmptyFile("test.out");
+       assertEmptyFile("test.err");
+       assertEqualInt(0, chdir(".."));
+
+       /* Test 2: -q foo bar should extract up to the first bar. */
+       assertEqualInt(0, mkdir("test2", 0755));
+       assertEqualInt(0, chdir("test2"));
+       assertEqualInt(0,
+           systemf("%s -xf ../archive.tar -q foo bar >test.out 2>test.err", testprog));
+       assertFileContents("foo2", 4, "foo");
+       assertFileContents("bar1", 4, "bar");
+       assertEmptyFile("test.out");
+       assertEmptyFile("test.err");
+       assertEqualInt(0, chdir(".."));
+
+       /* Test 3: Same as test 2, but use --fast-read spelling. */
+       assertEqualInt(0, mkdir("test3", 0755));
+       assertEqualInt(0, chdir("test3"));
+       assertEqualInt(0,
+           systemf("%s -xf ../archive.tar --fast-read foo bar >test.out 2>test.err", testprog));
+       assertFileContents("foo2", 4, "foo");
+       assertFileContents("bar1", 4, "bar");
+       assertEmptyFile("test.out");
+       assertEmptyFile("test.err");
+       assertEqualInt(0, chdir(".."));
+
+       /* Test 4: Without -q, should extract everything. */
+       assertEqualInt(0, mkdir("test4", 0755));
+       assertEqualInt(0, chdir("test4"));
+       assertEqualInt(0,
+           systemf("%s -xf ../archive.tar foo bar >test.out 2>test.err", testprog));
+       assertFileContents("foo3", 4, "foo");
+       assertFileContents("bar2", 4, "bar");
+       assertEmptyFile("test.out");
+       assertEmptyFile("test.err");
+       assertEqualInt(0, chdir(".."));
+}
index b3e61d75ab7fb53fc09c0952e3475d528846113d..227b4a53d4165ede00613e6707ad7e4b6eb6decc 100644 (file)
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 #include "test.h"
-__FBSDID("$FreeBSD: src/usr.bin/tar/test/test_patterns.c,v 1.2 2008/08/15 06:12:02 kientzle Exp $");
+__FBSDID("$FreeBSD: src/usr.bin/tar/test/test_patterns.c,v 1.6 2008/08/21 22:28:00 kientzle Exp $");
 
 DEFINE_TEST(test_patterns)
 {
        int fd, r;
-       const char *reffile1 = "test_patterns.tgz";
-       const char *reffile1_out = "test_patterns.tgz.out";
-       const char *reffile1_err = "test_patterns.tgz.err";
+       const char *reffile2 = "test_patterns_2.tgz";
+       const char *reffile3 = "test_patterns_3.tgz";
+       const char *p;
 
        /*
         * Test basic command-line pattern handling.
         */
 
        /*
+        * Test 1: Files on the command line that don't get matched
+        * didn't produce an error.
+        *
         * John Baldwin reported this problem in PR bin/121598
         */
        fd = open("foo", O_CREAT | O_WRONLY, 0644);
@@ -48,13 +51,50 @@ DEFINE_TEST(test_patterns)
        failure("tar should return non-zero because a file was given on the command line that's not in the archive");
        assert(r != 0);
 
-       extract_reference_file(reffile1);
-       extract_reference_file(reffile1_out);
-       extract_reference_file(reffile1_err);
+       /*
+        * Test 2: Check basic matching of full paths that start with /
+        */
+       extract_reference_file(reffile2);
 
        r = systemf("%s tf %s /tmp/foo/bar > tar2a.out 2> tar2a.err",
-           testprog, reffile1);
+           testprog, reffile2);
+       assertEqualInt(r, 0);
+       p = "/tmp/foo/bar/\n/tmp/foo/bar/baz\n";
+       assertFileContents(p, strlen(p), "tar2a.out");
+       assertEmptyFile("tar2a.err");
+
+       /*
+        * Test 3 archive has some entries starting with '/' and some not.
+        */
+       extract_reference_file(reffile3);
+
+       /* Test 3a:  Pattern tmp/foo/bar should not match /tmp/foo/bar */
+       r = systemf("%s xf %s tmp/foo/bar > tar3a.out 2> tar3a.err",
+           testprog, reffile3);
+       assert(r != 0);
+       assertEmptyFile("tar3a.out");
+
+       /* Test 3b:  Pattern /tmp/foo/baz should not match tmp/foo/baz */
+       assertNonEmptyFile("tar3a.err");
+       /* Again, with the '/' */
+       r = systemf("%s xf %s /tmp/foo/baz > tar3b.out 2> tar3b.err",
+           testprog, reffile3);
+       assert(r != 0);
+       assertEmptyFile("tar3b.out");
+       assertNonEmptyFile("tar3b.err");
+
+       /* Test 3c: ./tmp/foo/bar should not match /tmp/foo/bar */
+       r = systemf("%s xf %s ./tmp/foo/bar > tar3c.out 2> tar3c.err",
+           testprog, reffile3);
+       assert(r != 0);
+       assertEmptyFile("tar3c.out");
+       assertNonEmptyFile("tar3c.err");
+
+       /* Test 3d: ./tmp/foo/baz should match tmp/foo/baz */
+       r = systemf("%s xf %s ./tmp/foo/baz > tar3d.out 2> tar3d.err",
+           testprog, reffile3);
        assertEqualInt(r, 0);
-       assertEqualFile("tar2a.out", reffile1_out);
-       assertEqualFile("tar2a.err", reffile1_err);
+       assertEmptyFile("tar3d.out");
+       assertEmptyFile("tar3d.err");
+       assertEqualInt(0, access("tmp/foo/baz/bar", F_OK));
 }
diff --git a/tar/test/test_patterns.tgz.err.uu b/tar/test/test_patterns.tgz.err.uu
deleted file mode 100644 (file)
index 258082a..0000000
+++ /dev/null
@@ -1,6 +0,0 @@
-$FreeBSD: src/usr.bin/tar/test/test_patterns.tgz.err.uu,v 1.1 2008/08/15 06:12:02 kientzle Exp $
-begin 644 test_patterns.tgz.err
-M8G-D=&%R.B!296UO=FEN9R!L96%D:6YG("<O)R!F<F]M(&UE;6)E<B!N86UE
-"<PH`
-`
-end
diff --git a/tar/test/test_patterns.tgz.out.uu b/tar/test/test_patterns.tgz.out.uu
deleted file mode 100644 (file)
index 07cc1a5..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-$FreeBSD: src/usr.bin/tar/test/test_patterns.tgz.out.uu,v 1.1 2008/08/15 06:12:02 kientzle Exp $
-begin 644 test_patterns.tgz.out
-==&UP+V9O;R]B87(O"G1M<"]F;V\O8F%R+V)A>@H`
-`
-end
similarity index 68%
rename from tar/test/test_patterns.tgz.uu
rename to tar/test/test_patterns_2.tgz.uu
index 1171e58dc828b3946cdc27f824caa883f112049c..bb58aff8eee315271ccbfda5962cf5f119182132 100644 (file)
@@ -1,5 +1,5 @@
-$FreeBSD: src/usr.bin/tar/test/test_patterns.tgz.uu,v 1.1 2008/08/15 06:12:02 kientzle Exp $
-begin 644 test_patterns.tgz
+$FreeBSD: src/usr.bin/tar/test/test_patterns_2.tgz.uu,v 1.1 2008/08/20 06:01:53 kientzle Exp $
+begin 644 test_patterns_2.tgz
 M'XL(`,P5I4@``^W3T0J",!3&<1]E;[!SYC:?Q\`H2`PS@IZ^F5AV(PFMJ__O
 MYB@;>.:W8X?V;/==9XM\1*0*P:2J59"QCN8ZO:A*4*<NAFA$G?=:F)"QIY?K
 M9:C[U,IP;%?WW0Y-<UI9_SR4^6F/&=DY_UW=Y[H#V_(O4_ZE$T?^_[#(_Y[K
diff --git a/tar/test/test_patterns_3.tgz.uu b/tar/test/test_patterns_3.tgz.uu
new file mode 100644 (file)
index 0000000..baf7cfa
--- /dev/null
@@ -0,0 +1,8 @@
+$FreeBSD: src/usr.bin/tar/test/test_patterns_3.tgz.uu,v 1.1 2008/08/21 07:04:57 kientzle Exp $
+begin 644 test_patterns_3.tgz
+M'XL(`)P/K4@``^W5T0K"(!3&\3V*;^#1H3Z/@T5!8[&,H*=O%J/M9M3(7?U_
+M-T?1BR.?HD[=11_Z7C=QT%49(A*<4V,UP4FNV53?$V/$U3;OLTK,./*5<H7Z
+M6;A=4QS&5M*I6]UW/[;M>65]>2CUUQX+TO/\F_@H<0<VY!^\)?\]?.(O$OW+
+K3_E[R?F;FO>_BWG^I;Z`#?D'X?T#``````````````!\Y0FE&!YR`"@`````
+`
+end