[Git][reproducible-builds/diffoscope][master] Support .deb archives that contain an uncompressed data.tar. Thanks to Roderich…

Chris Lamb gitlab at salsa.debian.org
Mon Jul 9 19:18:33 CEST 2018


Chris Lamb pushed to branch master at Reproducible Builds / diffoscope


Commits:
185077c8 by Chris Lamb at 2018-07-09T19:18:23+02:00
Support .deb archives that contain an uncompressed data.tar. Thanks to Roderich Schupp <roderich.schupp at gmail.com> for the bug report. (Closes: #903401)

- - - - -


5 changed files:

- diffoscope/comparators/deb.py
- diffoscope/comparators/utils/libarchive.py
- tests/comparators/test_deb.py
- + tests/data/bug903401_1.deb
- + tests/data/bug903401_2.deb


Changes:

=====================================
diffoscope/comparators/deb.py
=====================================
--- a/diffoscope/comparators/deb.py
+++ b/diffoscope/comparators/deb.py
@@ -201,6 +201,6 @@ class DebDataTarFile(File):
             isinstance(file.container.source.container.source, DebFile)
 
     def compare_details(self, other, source=None):
-        return [Difference.from_text_readers(list_libarchive(self.path),
-                                             list_libarchive(other.path),
+        return [Difference.from_text_readers(list_libarchive(self.path, ignore_errors=True),
+                                             list_libarchive(other.path, ignore_errors=True),
                                              self.path, other.path, source="file list")]


=====================================
diffoscope/comparators/utils/libarchive.py
=====================================
--- a/diffoscope/comparators/utils/libarchive.py
+++ b/diffoscope/comparators/utils/libarchive.py
@@ -95,32 +95,36 @@ libarchive.ArchiveEntry.pathname = property(lambda self: libarchive.ffi.entry_pa
     self._entry_p).decode('utf-8', errors='surrogateescape'))
 
 
-def list_libarchive(path):
-    with libarchive.file_reader(path) as archive:
-        for entry in archive:
-            if entry.isblk or entry.ischr:
-                size_or_dev = '{major:>3},{minor:>3}'.format(
-                    major=entry.rdevmajor, minor=entry.rdevminor)
-            else:
-                size_or_dev = entry.size
-            mtime = time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime(entry.mtime)
-                                  ) + '.{:06d}'.format(entry.mtime_nsec // 1000)
-            if entry.issym:
-                name_and_link = '{entry.name} -> {entry.linkname}'.format(
-                    entry=entry)
-            else:
-                name_and_link = entry.name
-            if entry.uname:
-                user = '{user:<8} {uid:>7}'.format(user=entry.uname.decode(
-                    'utf-8', errors='surrogateescape'), uid='({})'.format(entry.uid))
-            else:
-                user = entry.uid
-            if entry.gname:
-                group = '{group:<8} {gid:>7}'.format(group=entry.gname.decode(
-                    'utf-8', errors='surrogateescape'), gid='({})'.format(entry.gid))
-            else:
-                group = entry.gid
-            yield '{strmode} {entry.nlink:>3} {user:>8} {group:>8} {size_or_dev:>8} {mtime:>8} {name_and_link}\n'.format(strmode=entry.strmode.decode('us-ascii'), entry=entry, user=user, group=group, size_or_dev=size_or_dev, mtime=mtime, name_and_link=name_and_link)
+def list_libarchive(path, ignore_errors=False):
+    try:
+        with libarchive.file_reader(path) as archive:
+            for entry in archive:
+                if entry.isblk or entry.ischr:
+                    size_or_dev = '{major:>3},{minor:>3}'.format(
+                        major=entry.rdevmajor, minor=entry.rdevminor)
+                else:
+                    size_or_dev = entry.size
+                mtime = time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime(entry.mtime)
+                                      ) + '.{:06d}'.format(entry.mtime_nsec // 1000)
+                if entry.issym:
+                    name_and_link = '{entry.name} -> {entry.linkname}'.format(
+                        entry=entry)
+                else:
+                    name_and_link = entry.name
+                if entry.uname:
+                    user = '{user:<8} {uid:>7}'.format(user=entry.uname.decode(
+                        'utf-8', errors='surrogateescape'), uid='({})'.format(entry.uid))
+                else:
+                    user = entry.uid
+                if entry.gname:
+                    group = '{group:<8} {gid:>7}'.format(group=entry.gname.decode(
+                        'utf-8', errors='surrogateescape'), gid='({})'.format(entry.gid))
+                else:
+                    group = entry.gid
+                yield '{strmode} {entry.nlink:>3} {user:>8} {group:>8} {size_or_dev:>8} {mtime:>8} {name_and_link}\n'.format(strmode=entry.strmode.decode('us-ascii'), entry=entry, user=user, group=group, size_or_dev=size_or_dev, mtime=mtime, name_and_link=name_and_link)
+    except libarchive.exception.ArchiveError:
+        if not ignore_errors:
+            raise
 
 
 class LibarchiveMember(ArchiveMember):
@@ -211,11 +215,14 @@ class LibarchiveContainer(Archive):
         raise KeyError('%s not found in archive', member_name)
 
     def get_filtered_members(self):
-        with libarchive.file_reader(self.source.path) as archive:
-            for entry in archive:
-                if any_excluded(entry.pathname):
-                    continue
-                yield entry.pathname, self.get_subclass(entry)
+        try:
+            with libarchive.file_reader(self.source.path) as archive:
+                for entry in archive:
+                    if any_excluded(entry.pathname):
+                        continue
+                    yield entry.pathname, self.get_subclass(entry)
+        except libarchive.exception.ArchiveError:
+            pass
 
     def extract(self, member_name, dest_dir):
         self.ensure_unpacked()


=====================================
tests/comparators/test_deb.py
=====================================
--- a/tests/comparators/test_deb.py
+++ b/tests/comparators/test_deb.py
@@ -132,6 +132,8 @@ bug881937_deb1 = load_fixture('bug881937_1.deb')
 bug881937_deb2 = load_fixture('bug881937_2.deb')
 bug903391_deb1 = load_fixture('bug903391_1.deb')
 bug903391_deb2 = load_fixture('bug903391_2.deb')
+bug903401_deb1 = load_fixture('bug903401_1.deb')
+bug903401_deb2 = load_fixture('bug903401_2.deb')
 
 
 @skip_unless_tools_exist('xz')
@@ -143,5 +145,9 @@ def test_compare_different_compression(bug881937_deb1, bug881937_deb2):
     assert difference.details[1].details[2].details[1].unified_diff == expected_diff
 
 
+def test_uncompressed_data_tar(bug903401_deb1, bug903401_deb2):
+    bug903401_deb1.compare(bug903401_deb2)
+
+
 def test_uncompressed_control_tar(bug903391_deb1, bug903391_deb2):
     bug903391_deb1.compare(bug903391_deb2)


=====================================
tests/data/bug903401_1.deb
=====================================
Binary files /dev/null and b/tests/data/bug903401_1.deb differ


=====================================
tests/data/bug903401_2.deb
=====================================
Binary files /dev/null and b/tests/data/bug903401_2.deb differ



View it on GitLab: https://salsa.debian.org/reproducible-builds/diffoscope/commit/185077c843e2f61c3915dab73770867067cb9358

-- 
View it on GitLab: https://salsa.debian.org/reproducible-builds/diffoscope/commit/185077c843e2f61c3915dab73770867067cb9358
You're receiving this email because of your account on salsa.debian.org.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.reproducible-builds.org/pipermail/rb-commits/attachments/20180709/e8b561ba/attachment.html>


More information about the rb-commits mailing list