[Reproducible-commits] [dpkg] 61/63: dpkg-genbuildinfo: Rewrite Build-Environment generator

Jérémy Bobbio lunar at moszumanska.debian.org
Fri Mar 4 17:44:46 UTC 2016


This is an automated email from the git hooks/post-receive script.

lunar pushed a commit to branch pu/buildinfo
in repository dpkg.

commit 0298a4bfc33fe93c9074ea23ddb4e91ba0996a14
Author: Jérémy Bobbio <lunar at debian.org>
Date:   Sun Jan 31 00:18:15 2016 +0000

    dpkg-genbuildinfo: Rewrite Build-Environment generator
    
    The new code is less nice but should properly handle virtual
    packages, build profiles and architecture-qualified dependencies.
---
 scripts/dpkg-genbuildinfo.pl | 85 +++++++++++++++++++++++++++++++-------------
 1 file changed, 61 insertions(+), 24 deletions(-)

diff --git a/scripts/dpkg-genbuildinfo.pl b/scripts/dpkg-genbuildinfo.pl
index 7e9fa32..d0296f1 100755
--- a/scripts/dpkg-genbuildinfo.pl
+++ b/scripts/dpkg-genbuildinfo.pl
@@ -123,7 +123,7 @@ sub parse_status {
 
         if (/^(?:Pre-)?Depends: (.*)$/m) {
             foreach (split(/,\s*/, $1)) {
-                push @{$depends{$package}}, $_;
+                push @{$depends{"$package:$arch"}}, $_;
             }
         }
     }
@@ -134,14 +134,17 @@ sub parse_status {
 
 sub append_deps {
     my $pkgs = shift;
-    my $deps;
 
     foreach my $dep_str (@_) {
         next unless $dep_str;
-        $deps = deps_parse($dep_str, reduce_restrictions => 1,
-                           build_dep => 1, build_profiles => \@build_profiles);
-        # add packages as unseen if they were not there before
-        deps_iterate($deps, sub { push @{$pkgs}, $_[0]->{package}; 1 });
+        my $deps = deps_parse($dep_str, reduce_restrictions => 1,
+                              build_dep => 1, build_profiles => \@build_profiles);
+        # We add every sub-dependencies as we can't know which package in an OR
+        # dependency has been effectively used.
+        deps_iterate($deps, sub {
+            push @{$pkgs},
+                $_[0]->{package} . (defined $_[0]->{archqual} ? ':' . $_[0]->{archqual} : '');
+            1 });
     }
 }
 
@@ -290,7 +293,6 @@ if ($always_include_path) {
 $checksums->export_to_control($fields);
 
 my ($facts, $depends, $essential_pkgs) = parse_status("$admindir/status");
-my $deps;
 my %seen_pkgs;
 my @unprocessed_pkgs;
 
@@ -309,27 +311,62 @@ if ($include & BUILD_ARCH_INDEP) {
     append_deps(\@unprocessed_pkgs, $control->get_source->{'Build-Depends-Indep'});
 }
 
-while (my $pkg = shift @unprocessed_pkgs) {
-    next if $seen_pkgs{$pkg};
-    next unless defined $facts->{pkg}->{$pkg}->[0];
-    append_deps(\@unprocessed_pkgs, @{$depends->{$pkg}});
-    $seen_pkgs{$pkg} = 1;
-}
-
 my $environment = Dpkg::Deps::AND->new();
-foreach my $pkg (sort keys %seen_pkgs) {
-    foreach my $installed_pkg (@{$facts->{pkg}->{$pkg}}) {
-        my $version = $installed_pkg->{version};
-        my $architecture = $installed_pkg->{architecture};
-        my $pkg_name = $pkg;
-        if (defined $architecture &&
-            $architecture ne 'all' && $architecture ne $build_arch) {
-            $pkg_name = "$pkg_name:$architecture";
+while (my $pkg_name = shift @unprocessed_pkgs) {
+    next if $seen_pkgs{$pkg_name};
+    $seen_pkgs{$pkg_name} = 1;
+
+    my $required_architecture;
+    if ($pkg_name =~ /\A(.*):(.*)\z/) {
+        $pkg_name = $1;
+        my $arch = $2;
+        $required_architecture = $arch if $arch !~ /\A(all|any|native)\Z/
+    }
+    my $pkg;
+    my $qualified_pkg_name;
+    foreach my $installed_pkg (@{$facts->{pkg}->{$pkg_name}}) {
+        if (!defined $required_architecture || $required_architecture eq $installed_pkg->{architecture}) {
+            $pkg = $installed_pkg;
+            $qualified_pkg_name = $pkg_name . ':' . $installed_pkg->{architecture};
+            last;
+        }
+    }
+    if (defined $pkg) {
+        my $version = $pkg->{version};
+        my $architecture = $pkg->{architecture};
+        my $new_deps_str = defined $depends->{$qualified_pkg_name} ? deps_concat(@{$depends->{$qualified_pkg_name}}) : '';
+        my $new_deps = deps_parse($new_deps_str);
+        if (!defined $required_architecture) {
+            $environment->add(Dpkg::Deps::Simple->new("$pkg_name (= $version)"));
+        } else {
+            $environment->add(Dpkg::Deps::Simple->new("$qualified_pkg_name (= $version)"));
+            # Dependencies of foreign packages are also foreign packages (or Arch:all)
+            # so we need to qualify them as well. We figure out if the package is actually
+            # foreign by searching for an installed package of the right architecture.
+            deps_iterate($new_deps, sub {
+                my $dep = shift;
+                $dep->{archqual} //= $architecture
+                    if grep sub { $_[0]->{architecture} eq $architecture }, @{$facts->{pkg}->{$dep->{package}}};
+                1;
+            });
+        }
+        # We add every sub-dependencies as we can't know which package in an OR
+        # dependency has been effectively used.
+        deps_iterate($new_deps, sub {
+            push @unprocessed_pkgs,
+                $_[0]->{package} . (defined $_[0]->{archqual} ? ':' . $_[0]->{archqual} : '');
+            1 });
+    } elsif (defined $facts->{virtualpkg}->{$pkg_name}) {
+        # virtual package: we can't know for sure which implementation
+        # is the one that has been used, so let's add them all...
+        foreach my $provided (@{$facts->{virtualpkg}->{$pkg_name}}) {
+            my ($provided_by, $provided_rel, $provided_ver) = @{$provided};
+            push @unprocessed_pkgs, $provided_by;
         }
-        my $dep = Dpkg::Deps::Simple->new("$pkg_name (= $version)");
-        $environment->add($dep);
     }
+    # else: it's a package in an OR dependency that has been satisfied otherwise
 }
+$environment->sort();
 $environment = "\n" . $environment->output();
 $environment =~ s/, /,\n/g;
 $fields->{'Build-Environment'} = $environment;

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/reproducible/dpkg.git



More information about the Reproducible-commits mailing list