Package: devscripts
Version: 2.15.3+deb8u1
Severity: important
Tags: patch

Hi,

Trying to grab vlc 2.2.5-1 during the BSP in Paris this weekend (to
debug then file #862474), I only got the following files:
  vlc_2.2.4.orig-ffmpeg-2-8-11.tar.xz
  vlc_2.2.5-1.debian.tar.xz
  vlc_2.2.5-1.dsc
  vlc_2.2.5.orig.tar.xz

while of course the right ones would have been:
  vlc_2.2.5-1.debian.tar.xz
  vlc_2.2.5-1.dsc
  vlc_2.2.5.orig-ffmpeg-2-8-11.tar.xz
  vlc_2.2.5.orig.tar.xz

You'll find attached a patch which starts by downloading and parsing the
dsc file to extract the list of required filenames, which should help a
bit compared to the current “let's find one of the filenames which had
suitable contents” approach. Checking the presence of the source package
name at the beginning of the filename is not sufficient…

I've also checked the issue and its resolution for various versions of
vlc, and with all current versions of firefox-esr (using a loop over
rmadison's output).

Thanks for considering.


KiBi.
>From 07c7646dfd187da7c296a463561244de97a2a3ab Mon Sep 17 00:00:00 2001
From: Cyril Brulebois <k...@debian.org>
Date: Mon, 15 May 2017 16:13:14 +0200
Subject: [PATCH] debsnap: parse the dsc file when downloading source packages.

It's important to restore contents under the right filename for the
source package to be consistent, instead of picking one of the few
filenames referenced as having such contents. Symptomatic issue: a
source tarball with several tarballs, the extra ones being shared
between several upstreams version if they don't change, like ffmpeg
2.8.11 between vlc 2.2.4 and 2.2.5:
 - vlc_2.2.4.orig-ffmpeg-2-8-11.tar.xz
 - vlc_2.2.5.orig-ffmpeg-2-8-11.tar.xz

Let's restore contents under the right filename by looking it up in the
dsc file.
---
 scripts/debsnap.pl | 65 +++++++++++++++++++++++++++++++++++++++++++++++-------
 1 file changed, 57 insertions(+), 8 deletions(-)

diff --git a/scripts/debsnap.pl b/scripts/debsnap.pl
index 8a3bf0f..90f5da2 100755
--- a/scripts/debsnap.pl
+++ b/scripts/debsnap.pl
@@ -334,24 +334,73 @@ else {
 	    next;
 	}
 
+	# Get the dsc file and parse it to get the list of files to be
+	# restored (this should fix most issues with multi-tarball
+	# source packages):
+	my $dsc_name;
+	my $dsc_hash;
 	foreach my $hash (keys %{$src_json->{fileinfo}}) {
 	    my $fileinfo = $src_json->{fileinfo}{$hash};
-	    my $file_name;
-	    # fileinfo may match multiple files (e.g., orig tarball for iceweasel 3.0.12)
 	    foreach my $info (@$fileinfo) {
-		if ($info->{name} =~ m/^\Q${package}\E/) {
-		    $file_name = $info->{name};
+		if ($info->{name} =~ m/^\Q${package}\E_.*\.dsc/) {
+		    $dsc_name = $info->{name};
+		    $dsc_hash = $hash;
 		    last;
 		}
 	    }
-	    unless ($file_name) {
-		warn "$progname: No files with hash $hash matched '${package}'\n";
+	    last if $dsc_name;
+	}
+	unless ($dsc_name) {
+	    warn "$progname: No dsc file detected for $package version $version->{version}\n";
+	    $warnings++;
+	    next;
+	}
+
+	# Retrieve the dsc file:
+	my $file_url = "$opt{baseurl}/file/$dsc_hash";
+	if (!have_file("$opt{destdir}/$dsc_name", $dsc_hash)) {
+	    verbose "Getting dsc file $dsc_name: $file_url";
+	    $mkDestDir->();
+	    LWP::Simple::getstore($file_url, "$opt{destdir}/$dsc_name");
+	}
+
+	# Get the list of files from the dsc:
+	my @files;
+	open my $fh, '<', "$opt{destdir}/$dsc_name"
+	    or die "unable to open the dsc file $opt{destdir}/$dsc_name";
+	while (<$fh> !~ /^Files:/) { }
+	while (<$fh> =~ /^ (\S+) (\d+) (\S+)$/) {
+	    my ($checksum, $size, $file) = ($1, $2, $3);
+	    push @files, $file;
+	}
+	close $fh
+	    or die "unable to close the dsc file";
+
+	# Iterate over files and find the right contents:
+	foreach my $file_name (@files) {
+	    my $file_hash;
+	    foreach my $hash (keys %{$src_json->{fileinfo}}) {
+		my $fileinfo = $src_json->{fileinfo}{$hash};
+
+		foreach my $info (@{$fileinfo}) {
+		    if ($info->{name} eq $file_name) {
+			$file_hash = $hash;
+			last;
+		    }
+		}
+		last if $file_hash;
+	    }
+	    unless ($file_hash) {
+		# Warning: this next statement will only move to the
+		# next files, not the next package
+		print "$progname: No hash found for file $file_name needed by $package version $version->{version}\n";
 		$warnings++;
 		next;
 	    }
-	    my $file_url = "$opt{baseurl}/file/$hash";
+
+	    my $file_url = "$opt{baseurl}/file/$file_hash";
 	    $file_name = basename($file_name);
-	    if (!have_file("$opt{destdir}/$file_name", $hash)) {
+	    if (!have_file("$opt{destdir}/$file_name", $file_hash)) {
 		verbose "Getting file $file_name: $file_url";
 		$mkDestDir->();
 		LWP::Simple::getstore($file_url, "$opt{destdir}/$file_name");
-- 
2.1.4

Reply via email to