From 94b2321b76f38516c4d39e44f0efcbfb6bd245c0 Mon Sep 17 00:00:00 2001 From: CentOS Sources Date: Apr 10 2018 05:20:00 +0000 Subject: import tar-1.26-34.el7 --- diff --git a/SOURCES/tar-1.26-keep-directory-symlink-doc-and-test.patch b/SOURCES/tar-1.26-keep-directory-symlink-doc-and-test.patch new file mode 100644 index 0000000..9f0d61f --- /dev/null +++ b/SOURCES/tar-1.26-keep-directory-symlink-doc-and-test.patch @@ -0,0 +1,209 @@ +From 49b5cd11bc3d64b0316cfc5b7245d25e4f7f4fcd Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Thu, 19 Oct 2017 16:53:00 +0200 +Subject: [PATCH] test keep-directory-symlink + +Upstream commit: +From d06126f814563b01e598b85a8cc233604a2948f2 Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Tue, 28 Feb 2017 09:55:09 +0100 +Subject: [PATCH] Test and document --keep-directory-symlink + +* doc/tar.1: Document the option. +* tests/extrac20.at: New testcase. +* tests/Makefile.am: Mention extrac20. +* tests/testsuite.at: Likewise. +--- + tests/Makefile.am | 1 + + tests/extrac20.at | 151 +++++++++++++++++++++++++++++++++++++++++++++++++++++ + tests/testsuite.at | 2 +- + 3 files changed, 153 insertions(+), 1 deletion(-) + create mode 100644 tests/extrac20.at + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 094b71c..bd8d3e8 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -79,6 +79,7 @@ TESTSUITE_AT = \ + extrac09.at\ + extrac18.at\ + extrac19.at\ ++ extrac20.at\ + extrac10.at\ + extrac11.at\ + extrac12.at\ +diff --git a/tests/extrac20.at b/tests/extrac20.at +new file mode 100644 +index 0000000..dd9b00d +--- /dev/null ++++ b/tests/extrac20.at +@@ -0,0 +1,151 @@ ++# Process this file with autom4te to create testsuite. -*- Autotest -*- ++# ++# Test suite for GNU tar. ++# Copyright 2017 Free Software Foundation, Inc. ++ ++# This file is part of GNU tar. ++ ++# GNU tar is free software; you can redistribute it and/or modify ++# it under the terms of the GNU General Public License as published by ++# the Free Software Foundation; either version 3 of the License, or ++# (at your option) any later version. ++ ++# GNU tar is distributed in the hope that it will be useful, ++# but WITHOUT ANY WARRANTY; without even the implied warranty of ++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++# GNU General Public License for more details. ++ ++# You should have received a copy of the GNU General Public License ++# along with this program. If not, see . ++ ++AT_SETUP([keep-directory-symlink]) ++AT_KEYWORDS([extrac20 extract old-files keep-old-files]) ++ ++AT_TAR_CHECK([ ++AT_SORT_PREREQ ++ ++for i in a b c ++do ++ dir=in$i ++ mkdir -p $dir/root/dir $dir/root/dirsymlink ++ touch $dir/root/dirsymlink/file$i ++ test $i != a && touch $dir/root/dirsymlink/file.conflict ++ tar cf archive$i.tar -C $dir root ++done ++ ++prep() ++{ ++ echo "== $1 ==" ++ echo "== $1 ==" >&2 ++ backup_dir=$1 ++ dir=out ++ mkdir -p $dir/root/dir ++ ln -s dir $dir/root/dirsymlink ++ test $round = normal && cd $dir >/dev/null ++} ++ ++clean() ++{ ++ test $round = normal && cd .. >/dev/null ++ find $dir | sort ++ mv $dir $backup_dir ++} ++ ++# Expand to '-f ../$1' or '-f $1 -C $dir' depending on $round variable ++file_spec() ++{ ++ if test $round = normal ++ then ++ echo "-f ../$1" ++ else ++ echo "-f $1 -C $dir" ++ fi ++} ++ ++for round in normal dir ++do ++ # Check that 'dirsymlink' replaces 'dir' ++ prep without_option_$round ++ tar -x `file_spec archivea.tar` || exit 1 ++ tar -x `file_spec archiveb.tar` || exit 1 ++ clean ++ ++ # Keep directory symlink must keep root/dirsymlink ++ prep with_option_$round ++ tar -x --keep-directory-symlink `file_spec archivea.tar` || exit 1 ++ tar -x --keep-directory-symlink `file_spec archiveb.tar` || exit 1 ++ clean ++ ++ prep collision_$round ++ tar -x --keep-directory-symlink `file_spec archivea.tar` --keep-old-files || exit 1 ++ tar -x --keep-directory-symlink `file_spec archiveb.tar` --keep-old-files || exit 1 ++ tar -x --keep-directory-symlink `file_spec archivec.tar` --keep-old-files && exit 1 ++ clean ++done ++], ++[0], ++[== without_option_normal == ++out ++out/root ++out/root/dir ++out/root/dirsymlink ++out/root/dirsymlink/file.conflict ++out/root/dirsymlink/filea ++out/root/dirsymlink/fileb ++== with_option_normal == ++out ++out/root ++out/root/dir ++out/root/dir/file.conflict ++out/root/dir/filea ++out/root/dir/fileb ++out/root/dirsymlink ++== collision_normal == ++out ++out/root ++out/root/dir ++out/root/dir/file.conflict ++out/root/dir/filea ++out/root/dir/fileb ++out/root/dir/filec ++out/root/dirsymlink ++== without_option_dir == ++out ++out/root ++out/root/dir ++out/root/dirsymlink ++out/root/dirsymlink/file.conflict ++out/root/dirsymlink/filea ++out/root/dirsymlink/fileb ++== with_option_dir == ++out ++out/root ++out/root/dir ++out/root/dir/file.conflict ++out/root/dir/filea ++out/root/dir/fileb ++out/root/dirsymlink ++== collision_dir == ++out ++out/root ++out/root/dir ++out/root/dir/file.conflict ++out/root/dir/filea ++out/root/dir/fileb ++out/root/dir/filec ++out/root/dirsymlink ++], ++[== without_option_normal == ++== with_option_normal == ++== collision_normal == ++tar: root/dirsymlink/file.conflict: Cannot open: File exists ++tar: Exiting with failure status due to previous errors ++== without_option_dir == ++== with_option_dir == ++== collision_dir == ++tar: root/dirsymlink/file.conflict: Cannot open: File exists ++tar: Exiting with failure status due to previous errors ++]) ++ ++AT_CLEANUP ++ +diff --git a/tests/testsuite.at b/tests/testsuite.at +index f7f00ee..b540948 100644 +--- a/tests/testsuite.at ++++ b/tests/testsuite.at +@@ -234,9 +234,9 @@ m4_include([extrac14.at]) + m4_include([extrac15.at]) + m4_include([extrac16.at]) + m4_include([extrac17.at]) +- + m4_include([extrac18.at]) + m4_include([extrac19.at]) ++m4_include([extrac20.at]) + + m4_include([label01.at]) + m4_include([label02.at]) +-- +2.13.6 + diff --git a/SOURCES/tar-1.26-large-sparse-file-listing.patch b/SOURCES/tar-1.26-large-sparse-file-listing.patch new file mode 100644 index 0000000..c334250 --- /dev/null +++ b/SOURCES/tar-1.26-large-sparse-file-listing.patch @@ -0,0 +1,390 @@ +From 77cef4ee39ee083838e5cf2137b0f344b49afb6a Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Tue, 29 Jan 2013 10:39:30 +0100 +Subject: [PATCH 1/4] Fix bug in sparse file listing + +List posix archives containing sparse files >8GB correctly and do not fail. +This fixes also bug in format of listing for sparse files >8GB - now the +real size is printed instead of the effective one (this is not strictly +posix format related). + +* src/list.c: Remove redundant assignment. +* src/tar.h: Add new 'real_size' and 'real_size_set' fields in + tar_stat_info struct. +* src/xheader.c: Correctly handle (especially sparse) file sizes directly in + xheader_decode(). +--- + src/list.c | 1 - + src/tar.h | 4 ++++ + src/xheader.c | 15 ++++++++++++++- + 3 files changed, 18 insertions(+), 2 deletions(-) + +diff --git a/src/list.c b/src/list.c +index dd501a9..6db36d1 100644 +--- a/src/list.c ++++ b/src/list.c +@@ -670,7 +670,6 @@ decode_header (union block *header, struct tar_stat_info *stat_info, + } + } + +- stat_info->archive_file_size = stat_info->stat.st_size; + xheader_decode (stat_info); + + if (sparse_member_p (stat_info)) +diff --git a/src/tar.h b/src/tar.h +index b181e58..690c146 100644 +--- a/src/tar.h ++++ b/src/tar.h +@@ -327,6 +327,10 @@ struct tar_stat_info + size_t sparse_map_size; /* Size of the sparse map */ + struct sp_array *sparse_map; + ++ off_t real_size; /* The real size of sparse file */ ++ int real_size_set; /* True when GNU.sparse.realsize is set in ++ archived file */ ++ + size_t xattr_map_size; /* Size of the xattr map */ + struct xattr_array *xattr_map; + +diff --git a/src/xheader.c b/src/xheader.c +index be793d4..708aece 100644 +--- a/src/xheader.c ++++ b/src/xheader.c +@@ -764,6 +764,16 @@ xheader_decode (struct tar_stat_info *st) + continue; + } + run_override_list (keyword_override_list, st); ++ ++ /* The archived (effective) file size is always set directly in tar header ++ field, possibly overridden by "size" extended header - in both cases, ++ result is now decoded in st->stat.st_size */ ++ st->archive_file_size = st->stat.st_size; ++ ++ /* The real file size (given by stat()) may be redefined for sparse ++ files in "GNU.sparse.realsize" extended header */ ++ if (st->real_size_set) ++ st->stat.st_size = st->real_size; + } + + static void +@@ -1438,7 +1435,10 @@ sparse_size_decoder (struct tar_stat_info *st, + { + uintmax_t u; + if (decode_num (&u, arg, TYPE_MAXIMUM (off_t), keyword)) +- st->stat.st_size = u; ++ { ++ st->real_size_set = 1; ++ st->real_size = u; ++ } + } + + static void +-- +2.13.5 + + +From 198d4621b2a367986c71cd2489c1465ec3be89dc Mon Sep 17 00:00:00 2001 +From: Sergey Poznyakoff +Date: Fri, 7 Nov 2014 11:47:44 +0200 +Subject: [PATCH 2/4] Add testcase for the previous commit. + +* tests/sparse05.at: New file. +* tests/Makefile.am: Add sparse05.at +* tests/testsuite.at: Include sparse05.at +--- + tests/Makefile.am | 1 + + tests/sparse05.at | 46 ++++++++++++++++++++++++++++++++++++++++++++++ + tests/testsuite.at | 1 + + 3 files changed, 48 insertions(+) + create mode 100644 tests/sparse05.at + +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 8e1ef8d..094b71c 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -171,6 +171,7 @@ TESTSUITE_AT = \ + sparse02.at\ + sparse03.at\ + sparse04.at\ ++ sparse05.at\ + sparsemv.at\ + sparsemvp.at\ + spmvp00.at\ +diff --git a/tests/sparse05.at b/tests/sparse05.at +new file mode 100644 +index 0000000..72f3274 +--- /dev/null ++++ b/tests/sparse05.at +@@ -0,0 +1,46 @@ ++# Process this file with autom4te to create testsuite. -*- Autotest -*- ++# ++# Test suite for GNU tar. ++# Copyright 2014 Free Software Foundation, Inc. ++ ++# This file is part of GNU tar. ++ ++# GNU tar is free software; you can redistribute it and/or modify ++# it under the terms of the GNU General Public License as published by ++# the Free Software Foundation; either version 3 of the License, or ++# (at your option) any later version. ++ ++# GNU tar is distributed in the hope that it will be useful, ++# but WITHOUT ANY WARRANTY; without even the implied warranty of ++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++# GNU General Public License for more details. ++ ++# You should have received a copy of the GNU General Public License ++# along with this program. If not, see . ++ ++AT_SETUP([listing sparse files bigger than 2^33 B]) ++AT_KEYWORDS([sparse sparse05]) ++ ++# Description: If an archive in POSIX.1-2001 archive contained a sparse file ++# member whose real size (excluding zero blocks) is bigger than 2^33 bytes, ++# tar 1.28 would incorrectly list the real member size. ++# Reported by: Pavel Raiskup ++# References: <1359119879.15037.4.camel@raiskup>, ++# http://lists.gnu.org/archive/html/bug-tar/2013-01/msg00001.html ++ ++AT_TAR_CHECK([ ++(echo 0 =2560 ++for i in `seq 1 999`; do ++ echo 10M =2560 ++done) | genfile --sparse --file BIGFILE --block-size 4K - || AT_SKIP_TEST ++tar -f - -c --sparse --posix BIGFILE | tar tvf - | awk '{ print $3, $(NF) }' ++], ++[0], ++[20961034240 BIGFILE ++], ++[], ++[], ++[], ++[pax]) ++ ++AT_CLEANUP +diff --git a/tests/testsuite.at b/tests/testsuite.at +index 3eb0eee..f7f00ee 100644 +--- a/tests/testsuite.at ++++ b/tests/testsuite.at +@@ -308,6 +308,7 @@ m4_include([sparse01.at]) + m4_include([sparse02.at]) + m4_include([sparse03.at]) + m4_include([sparse04.at]) ++m4_include([sparse05.at]) + m4_include([sparsemv.at]) + m4_include([spmvp00.at]) + m4_include([spmvp01.at]) +-- +2.13.5 + + +From 8a795036f08bca508c3f3425f41c566562573e5f Mon Sep 17 00:00:00 2001 +From: Sergey Poznyakoff +Date: Fri, 7 Nov 2014 11:37:33 +0200 +Subject: [PATCH 3/4] genfile: improve sparse mode + +Paxutils: 45af1632aa64a5ba1b108e248920e67c180e8485 + +* tests/genfile.c (generate_sparse_file): Handle '-' argument +(read from stdin); +If content strings starts with '=', treat it as fragment size and +use default pattern to fill it. +* doc/genfile.texi: Document changes to genfile. +--- + doc/genfile.texi | 31 +++++++++++++++------- + tests/genfile.c | 79 +++++++++++++++++++++++++++++++++++++++++++++++++------- + 2 files changed, 91 insertions(+), 19 deletions(-) + +diff --git a/doc/genfile.texi b/doc/genfile.texi +index b37e26e..b993b9b 100644 +--- a/doc/genfile.texi ++++ b/doc/genfile.texi +@@ -124,9 +124,8 @@ the rest of the command line specifies a so-called @dfn{file map}. + descriptors}. Each descriptor is composed of two values: a number, + specifying fragment offset from the end of the previous fragment or, + for the very first fragment, from the beginning of the file, and +-@dfn{contents string}, i.e., a string of characters, specifying the +-pattern to fill the fragment with. File offset can be suffixed with +-the following quantifiers: ++@dfn{contents string}, that specifies the pattern to fill the fragment ++with. File offset can be suffixed with the following quantifiers: + + @table @samp + @item k +@@ -140,17 +139,29 @@ The number is expressed in megabytes. + The number is expressed in gigabytes. + @end table + +- For each letter in contents string @command{genfile} will generate +-a @dfn{block} of data, filled with this letter and will write it to +-the fragment. The size of block is given by @option{--block-size} +-option. It defaults to 512. Thus, if the string consists of @var{n} +-characters, the resulting file fragment will contain +-@code{@var{n}*@var{block-size}} of data. ++ Contents string can be either a fragment size or a pattern. ++Fragment size is a decimal number, prefixed with an equals sign. It ++can be suffixed with a quantifier, as discussed above. If fragment ++size is given, the fragment of that size will be filled with the ++currently selected pattern (@pxref{Generate Mode, --pattern}) and ++written to the file. + +- Last fragment descriptor can have only file offset part. In this ++ A pattern is a string of arbitrary ASCII characters. For each ++of them, @command{genfile} will generate a @dfn{block} of data, ++filled with that character and will write it to the fragment. The size ++of block is given by @option{--block-size} option. It defaults to 512. ++Thus, if pattern consists of @var{n} characters, the resulting file ++fragment will contain @code{@var{n}*@var{block-size}} bytes of data. ++ ++ The last fragment descriptor can have only file offset part. In this + case @command{genfile} will create a hole at the end of the file up to + the given offset. + ++ A dash appearing as a fragment descriptor instructs ++@command{genfile} to read file map from the standard input. Each line ++of input should consist of fragment offset and contents string, ++separated by any amount of whitespace. ++ + For example, consider the following invocation: + + @smallexample +diff --git a/tests/genfile.c b/tests/genfile.c +index fa480ef..d41336b 100644 +--- a/tests/genfile.c ++++ b/tests/genfile.c +@@ -32,6 +32,7 @@ + #include + #include + #include ++#include + #define obstack_chunk_alloc malloc + #define obstack_chunk_free free + #include +@@ -506,6 +507,53 @@ mksparse (int fd, off_t displ, char *marks) + } + } + ++static int ++make_fragment (int fd, char *offstr, char *mapstr) ++{ ++ int i; ++ off_t displ = get_size (offstr, 1); ++ ++ file_length += displ; ++ ++ if (!mapstr || !*mapstr) ++ { ++ mkhole (fd, displ); ++ return 1; ++ } ++ else if (*mapstr == '=') ++ { ++ off_t n = get_size (mapstr + 1, 1); ++ ++ switch (pattern) ++ { ++ case DEFAULT_PATTERN: ++ for (i = 0; i < block_size; i++) ++ buffer[i] = i & 255; ++ break; ++ ++ case ZEROS_PATTERN: ++ memset (buffer, 0, block_size); ++ break; ++ } ++ ++ if (lseek (fd, displ, SEEK_CUR) == -1) ++ error (EXIT_FAILURE, errno, "lseek"); ++ ++ for (; n; n--) ++ { ++ if (write (fd, buffer, block_size) != block_size) ++ error (EXIT_FAILURE, errno, "write"); ++ file_length += block_size; ++ } ++ } ++ else ++ { ++ file_length += block_size * strlen (mapstr); ++ mksparse (fd, displ, mapstr); ++ } ++ return 0; ++} ++ + static void + generate_sparse_file (int argc, char **argv) + { +@@ -526,20 +574,33 @@ generate_sparse_file (int argc, char **argv) + + file_length = 0; + +- for (i = 0; i < argc; i += 2) ++ while (argc) + { +- off_t displ = get_size (argv[i], 1); +- file_length += displ; ++ if (argv[0][0] == '-' && argv[0][1] == 0) ++ { ++ char buf[256]; ++ while (fgets (buf, sizeof (buf), stdin)) ++ { ++ size_t n = strlen (buf); + +- if (i == argc-1) +- { +- mkhole (fd, displ); +- break; ++ while (n > 0 && c_isspace (buf[n-1])) ++ buf[--n] = 0; ++ ++ n = strcspn (buf, " \t"); ++ buf[n++] = 0; ++ while (buf[n] && c_isblank (buf[n])) ++ ++n; ++ make_fragment (fd, buf, buf + n); ++ } ++ ++argv; ++ --argc; + } + else + { +- file_length += block_size * strlen (argv[i+1]); +- mksparse (fd, displ, argv[i+1]); ++ if (make_fragment (fd, argv[0], argv[1])) ++ break; ++ argc -= 2; ++ argv += 2; + } + } + +-- +2.13.5 + + +From 29e35df407d6c7b1e1ff57f7ef2030a253132a8a Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Fri, 4 Dec 2015 19:36:14 +0100 +Subject: [PATCH 4/4] genfile: remove unused variable + +paxutils: 58b8ac114790e2de7992db1a387ec14238783f39 + +* tests/genfile.c (generate_sparse_file): Remove unused 'i'. +--- + tests/genfile.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/tests/genfile.c b/tests/genfile.c +index d41336b..4699d21 100644 +--- a/tests/genfile.c ++++ b/tests/genfile.c +@@ -557,7 +557,6 @@ make_fragment (int fd, char *offstr, char *mapstr) + static void + generate_sparse_file (int argc, char **argv) + { +- int i; + int fd; + int flags = O_CREAT | O_RDWR | O_BINARY; + +-- +2.13.5 + diff --git a/SOURCES/tar-1.26-non-deterministic-archive-detection.patch b/SOURCES/tar-1.26-non-deterministic-archive-detection.patch new file mode 100644 index 0000000..1f57fe9 --- /dev/null +++ b/SOURCES/tar-1.26-non-deterministic-archive-detection.patch @@ -0,0 +1,78 @@ + +From 1847ec67cec36a17354115374954fea211d1f0da Mon Sep 17 00:00:00 2001 +From: Sergey Poznyakoff +Date: Thu, 19 Feb 2015 17:00:58 +0200 +Subject: [PATCH] Improve compression format recognition + +Some comressed archives can pass the checksum test, which makes tar +treat them as uncompressed archives. + +* src/buffer.c (check_compressed_archive): Test the checksum only +if the block we read looks like a valid tar header (i.e. has +a magic string). +--- + src/buffer.c | 5 ++++- + 1 file changed, 4 insertions(+), 1 deletion(-) + +diff --git a/src/buffer.c b/src/buffer.c +index a7d8971..1a96595 100644 +--- a/src/buffer.c ++++ b/src/buffer.c +@@ -391,7 +391,10 @@ check_compressed_archive (bool *pshort) + /* Restore global values */ + read_full_records = sfr; + +- if (tar_checksum (record_start, true) == HEADER_SUCCESS) ++ if ((strcmp (record_start->header.magic, TMAGIC) == 0 || ++ strcmp (record_start->buffer + offsetof (struct posix_header, magic), ++ OLDGNU_MAGIC) == 0) && ++ tar_checksum (record_start, true) == HEADER_SUCCESS) + /* Probably a valid header */ + return ct_tar; + +-- +2.13.5 + + + +From 1e8b786e651d174a5fc9bf63a08d00c2d592ee3e Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Thu, 30 Mar 2017 13:30:15 +0200 +Subject: [PATCH] Fix non-deterministic archive type detection + +Due to analysis of partly uninitialized read-ahead buffer +(short_read call), we sometimes mistakenly classified very small +compressed archives as non-compressed; which in turn caused +extraction failure. + +* src/buffer.c (check_compressed_archive): Don't assume that +archives smaller than BLOCKSIZE could be non-compressed, as tar +header always has at least one block. +--- + src/buffer.c | 10 ++++++---- + 1 file changed, 6 insertions(+), 4 deletions(-) + +diff --git a/src/buffer.c b/src/buffer.c +index 57fe813..6f96c2f 100644 +--- a/src/buffer.c ++++ b/src/buffer.c +@@ -402,10 +402,12 @@ check_compressed_archive (bool *pshort) + /* Restore global values */ + read_full_records = sfr; + +- if ((strcmp (record_start->header.magic, TMAGIC) == 0 || +- strcmp (record_start->buffer + offsetof (struct posix_header, magic), +- OLDGNU_MAGIC) == 0) && +- tar_checksum (record_start, true) == HEADER_SUCCESS) ++ if (record_start != record_end /* no files smaller than BLOCKSIZE */ ++ && (strcmp (record_start->header.magic, TMAGIC) == 0 ++ || strcmp (record_start->buffer + offsetof (struct posix_header, ++ magic), ++ OLDGNU_MAGIC) == 0) ++ && tar_checksum (record_start, true) == HEADER_SUCCESS) + /* Probably a valid header */ + return ct_tar; + +-- +2.13.5 + diff --git a/SOURCES/tar-1.26-xattrs-skip-old-files-hangs.patch b/SOURCES/tar-1.26-xattrs-skip-old-files-hangs.patch new file mode 100644 index 0000000..8db797d --- /dev/null +++ b/SOURCES/tar-1.26-xattrs-skip-old-files-hangs.patch @@ -0,0 +1,215 @@ +diff --git a/THANKS b/THANKS +index e87381f..6fa0a9e 100644 +--- a/THANKS ++++ b/THANKS +@@ -131,6 +131,7 @@ David Nugent davidn@blaze.net.au + David Shaw david.shaw@alcatel.com.au + David Steiner dsteiner@ispa.uni-osnabrueck.de + David Taylor taylor@think.com ++Dawid dpc@dpc.pw + Dean Gaudet dgaudet@watdragon.uwaterloo.ca + Demizu Noritoshi nori-d@is.aist-nara.ac.jp + Denis Excoffier denis.excoffier@free.fr +diff --git a/src/extract.c b/src/extract.c +index b622a2a..63e4d14 100644 +--- a/src/extract.c ++++ b/src/extract.c +@@ -745,13 +745,13 @@ maybe_recoverable (char *file_name, bool regular, bool *interdir_made) + in advance dramatically improves the following performance of reading and + writing a file). If not restoring permissions, invert the INVERT_PERMISSIONS + bits from the file's current permissions. TYPEFLAG specifies the type of the +- file. FILE_CREATED indicates set_xattr has created the file */ ++ file. Returns non-zero when error occurs (while un-available xattrs is not ++ an error, rather no-op). Non-zero FILE_CREATED indicates set_xattr has ++ created the file. */ + static int + set_xattr (char const *file_name, struct tar_stat_info const *st, + mode_t invert_permissions, char typeflag, int *file_created) + { +- int status = 0; +- + #ifdef HAVE_XATTRS + bool interdir_made = false; + +@@ -759,17 +759,32 @@ set_xattr (char const *file_name, struct tar_stat_info const *st, + { + mode_t mode = current_stat_info.stat.st_mode & MODE_RWX & ~ current_umask; + +- do +- status = mknodat (chdir_fd, file_name, mode ^ invert_permissions, 0); +- while (status && maybe_recoverable ((char *)file_name, false, +- &interdir_made)); ++ for (;;) ++ { ++ if (!mknodat (chdir_fd, file_name, mode ^ invert_permissions, 0)) ++ { ++ /* Successfully created file */ ++ xattrs_xattrs_set (st, file_name, typeflag, 0); ++ *file_created = 1; ++ return 0; ++ } + +- xattrs_xattrs_set (st, file_name, typeflag, 0); +- *file_created = 1; ++ switch (maybe_recoverable ((char *)file_name, false, &interdir_made)) ++ { ++ case RECOVER_OK: ++ continue; ++ case RECOVER_NO: ++ skip_member (); ++ open_error (file_name); ++ return 1; ++ case RECOVER_SKIP: ++ return 0; ++ } ++ } + } + #endif + +- return(status); ++ return 0; + } + + /* Fix the statuses of all directories whose statuses need fixing, and +@@ -1089,11 +1104,7 @@ extract_file (char *file_name, int typeflag) + int file_created = 0; + if (set_xattr (file_name, ¤t_stat_info, invert_permissions, + typeflag, &file_created)) +- { +- skip_member (); +- open_error (file_name); +- return 1; +- } ++ return 1; + + while ((fd = open_output_file (file_name, typeflag, mode, + file_created, ¤t_mode, +diff --git a/tests/Makefile.am b/tests/Makefile.am +index 2a70314..8e1ef8d 100644 +--- a/tests/Makefile.am ++++ b/tests/Makefile.am +@@ -200,6 +200,7 @@ TESTSUITE_AT = \ + xattr04.at\ + xattr05.at\ + xattr06.at\ ++ xattr07.at\ + acls01.at\ + acls02.at\ + acls03.at\ +diff --git a/tests/testsuite.at b/tests/testsuite.at +index ebce9cc..3eb0eee 100644 +--- a/tests/testsuite.at ++++ b/tests/testsuite.at +@@ -361,6 +361,7 @@ m4_include([xattr03.at]) + m4_include([xattr04.at]) + m4_include([xattr05.at]) + m4_include([xattr06.at]) ++m4_include([xattr07.at]) + + m4_include([acls01.at]) + m4_include([acls02.at]) +diff --git a/tests/xattr07.at b/tests/xattr07.at +new file mode 100644 +index 0000000..a834981 +--- /dev/null ++++ b/tests/xattr07.at +@@ -0,0 +1,73 @@ ++# Process this file with autom4te to create testsuite. -*- Autotest -*- ++# ++# Test suite for GNU tar. ++# Copyright 2011, 2013-2014, 2016 Free Software Foundation, Inc. ++ ++# This file is part of GNU tar. ++ ++# GNU tar is free software; you can redistribute it and/or modify ++# it under the terms of the GNU General Public License as published by ++# the Free Software Foundation; either version 3 of the License, or ++# (at your option) any later version. ++ ++# GNU tar is distributed in the hope that it will be useful, ++# but WITHOUT ANY WARRANTY; without even the implied warranty of ++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++# GNU General Public License for more details. ++ ++# You should have received a copy of the GNU General Public License ++# along with this program. If not, see . ++# ++# Test description: ++# Test that --keep-old-files doesn't change xattrs of already existing file. ++# Per report: ++# https://lists.gnu.org/archive/html/bug-tar/2016-10/msg00001.html ++ ++AT_SETUP([xattrs: xattrs and --skip-old-files]) ++AT_KEYWORDS([xattrs xattr07]) ++ ++AT_TAR_CHECK([ ++AT_XATTRS_PREREQ ++mkdir dir ++genfile --file dir/file ++genfile --file dir/file2 ++ ++setfattr -n user.test -v OurDirValue dir ++setfattr -n user.test -v OurFileValue dir/file ++setfattr -n user.test -v OurFileValue dir/file2 ++ ++tar --xattrs -cf archive.tar dir ++ ++setfattr -n user.test -v OurDirValue2 dir ++setfattr -n user.test -v OurFileValue2 dir/file ++setfattr -n user.test -v OurFileValue2 dir/file2 ++ ++# Check that tar continues to file2 too! ++tar --xattrs -xvf archive.tar --skip-old-files ++tar --xattrs -xvf archive.tar --keep-old-files ++ ++getfattr -h -d dir | grep -v -e '^#' -e ^$ ++getfattr -h -d dir/file | grep -v -e '^#' -e ^$ ++getfattr -h -d dir/file2 | grep -v -e '^#' -e ^$ ++], ++[0], ++[dir/ ++dir/file ++dir/file2 ++dir/ ++dir/file ++dir/file2 ++user.test="OurDirValue2" ++user.test="OurFileValue2" ++user.test="OurFileValue2" ++], [tar: dir: skipping existing file ++tar: dir/file: skipping existing file ++tar: dir/file: skipping existing file ++tar: dir/file2: skipping existing file ++tar: dir/file2: skipping existing file ++tar: dir/file: Cannot open: File exists ++tar: dir/file2: Cannot open: File exists ++tar: Exiting with failure status due to previous errors ++]) ++ ++AT_CLEANUP +From f2a7560718946e0920b55419f0953953bf824077 Mon Sep 17 00:00:00 2001 +From: Pavel Raiskup +Date: Mon, 28 Nov 2016 08:44:42 +0100 +Subject: [PATCH] tests: more deterministic xattr07 + +* tests/xattr07.at: Define order of files within tested archive. +--- + tests/xattr07.at | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/tests/xattr07.at b/tests/xattr07.at +index a834981..47d54b8 100644 +--- a/tests/xattr07.at ++++ b/tests/xattr07.at +@@ -36,7 +36,7 @@ setfattr -n user.test -v OurDirValue dir + setfattr -n user.test -v OurFileValue dir/file + setfattr -n user.test -v OurFileValue dir/file2 + +-tar --xattrs -cf archive.tar dir ++tar --xattrs --no-recursion -cf archive.tar dir dir/file dir/file2 + + setfattr -n user.test -v OurDirValue2 dir + setfattr -n user.test -v OurFileValue2 dir/file +-- +2.13.5 + diff --git a/SOURCES/tar.1 b/SOURCES/tar.1 index f062395..3beb97f 100644 --- a/SOURCES/tar.1 +++ b/SOURCES/tar.1 @@ -143,6 +143,9 @@ treat them as errors don't replace existing files that are newer than their archive copies .TP +\fB\-\-keep\-directory\-symlink\fR +Don't replace existing symlinks to directories when extracting. +.TP \fB\-\-no\-overwrite\-dir\fR preserve metadata of existing directories .TP diff --git a/SPECS/tar.spec b/SPECS/tar.spec index 7ec80bf..426fc82 100644 --- a/SPECS/tar.spec +++ b/SPECS/tar.spec @@ -5,7 +5,7 @@ Summary: A GNU file archiving program Name: tar Epoch: 2 Version: 1.26 -Release: 32%{?dist} +Release: 34%{?dist} License: GPLv3+ Group: Applications/Archiving URL: http://www.gnu.org/software/tar/ @@ -151,6 +151,27 @@ Patch23: tar-1.26-xattrs-exclude-include-repair.patch # ~> rhbz#1350640 Patch24: tar-1.26-keep-directory-symlink.patch +# Fix non-determinism in archive-type-heuristic +# ~> upstream: 1847ec67cec + 1e8b786e651 +# ~> rhbz#1437297 +Patch25: tar-1.26-non-deterministic-archive-detection.patch + +# Avoid tar to hang with --extract --xatrrs and --skip-old-files options +# ~> upstream: 597b0ae509 and ca9399d4e +# -> proposed: https://www.mail-archive.com/bug-tar@gnu.org/msg05229.html +# ~> rhbz#1408168 +Patch26: tar-1.26-xattrs-skip-old-files-hangs.patch + +# List sparse files of 8GB+ properly, without failure. +# ~> upstream: 586a6263e9d97 ec94fbdf458ad +# ~> paxutils-upstream: 45af1632aa64a 58b8ac114790e +Patch27: tar-1.26-large-sparse-file-listing.patch + +# Document (and test) --keep-directory-option +# ~> upstream: d06126f814563b01e598b85a8cc233604a2948f2 +# ~> rhbz#1504146 +Patch28: tar-1.26-keep-directory-symlink-doc-and-test.patch + # Silence gcc warnings # ~> upstream tar: 17f99bc6f, 5bb0433 # ~> upstream paxutils: 0b3d84a0 @@ -213,6 +234,10 @@ the rmt package on the remote box. %patch22 -p1 -b .directory %patch23 -p1 -b .xattrs-exclude-include %patch24 -p1 -b .keep-directory-symlink +%patch25 -p1 -b .fix-archive-detection-heuristic +%patch26 -p1 -b .extract-xattrs-hangs +%patch27 -p1 -b .large-sparse-file-listing +%patch28 -p1 -b .test-and-doc-for-keep-dir-symlink %patch999 -p1 -b .silence-gcc autoreconf -v @@ -271,6 +296,14 @@ fi %{_infodir}/tar.info* %changelog +* Thu Oct 19 2017 Pavel Raiskup - 1.26-34 +- document --keep-directory-symlink in manual page (rhbz#1504146) + +* Thu Sep 07 2017 Pavel Raiskup - 1.26-33 +- extract: deterministic archive type detection (rhbz#1437297) +- avoid hang when extracting with --xattrs --skip-old-files (rhbz#1408168) +- fix listing of large sparse members (rhbz#1347229) + * Tue Feb 28 2017 Tomas Repik - 2:1.26-32 - restore incremental backups correctly, files were not being removed (rhbz#1184697) - fix the behavior of tar when --directory option is used together with