[SCM] Debian package checker branch, master, updated. 2.2.13-7-ga5f818a
The following commit has been merged in the master branch:
commit a5f818a0c3b6ade7b4619fe65f1c093b91fa26e8
Author: Russ Allbery <rra@debian.org>
Date: Tue Jul 21 15:28:46 2009 -0700
Move build dependency debian/rules checks and fix pattern rules
* checks/fields{,.desc}
+ [RA] Move debian/rules parsing to check build dependencies to
checks/rules.
* checks/rules{,.desc}:
+ [RA] Moved checking of build dependencies based on programs invoked
in debian/rules from checks/fields to here.
+ [RA] Expand Lintian's understanding of which targets are run for the
clean target to include targets invoked via pattern variable
expansion. (Closes: #536405)
diff --git a/checks/fields b/checks/fields
index 6235b7b..161a8ad 100644
--- a/checks/fields
+++ b/checks/fields
@@ -105,98 +105,6 @@ our %known_x_metapackages = map { $_ => 1 }
( 'x-window-system', 'x-window-system-dev', 'x-window-system-core',
'xorg', 'xorg-dev', );
-# The allowed Python dependencies currently. This is the list of alternatives
-# that, either directly or through transitive dependencies that can be relied
-# upon, ensure /usr/bin/python will exist for the use of dh_python.
-our $PYTHON_DEPEND = 'python | python-dev | python-all | python-all-dev | '
- . join (' | ', map { "python$_ | python$_-dev" } qw(2.4 2.5));
-
-# Certain build tools must be listed in Build-Depends even if there are no
-# arch-specific packages because they're required in order to run the clean
-# rule. (See Policy 7.6.) The following is a list of package dependencies;
-# regular expressions that, if they match anywhere in the debian/rules file,
-# say that this package is allowed (and required) in Build-Depends; and
-# optional tags to use for reporting the problem if some information other
-# than the default is required.
-our @GLOBAL_CLEAN_DEPENDS = (
- [ ant => qr'^include\s*/usr/share/cdbs/1/rules/ant\.mk' ],
- [ cdbs => qr'^include\s+/usr/share/cdbs/' ],
- [ cdbs => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
- [ dbs => qr'^include\s+/usr/share/dbs/' ],
- [ 'dh-make-php' => qr'^include\s+/usr/share/cdbs/1/class/pear\.mk' ],
- [ debhelper => qr'^include\s+/usr/share/cdbs/1/rules/debhelper\.mk' ],
- [ debhelper => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
- [ dpatch => qr'^include\s+/usr/share/cdbs/1/rules/dpatch\.mk' ],
- [ 'gnome-pkg-tools' => qr'^include\s+/usr/share/gnome-pkg-tools/' ],
- [ quilt => qr'^include\s+/usr/share/cdbs/1/rules/patchsys-quilt\.mk' ],
- [ dpatch => qr'^include\s+/usr/share/dpatch/' ],
- [ quilt => qr'^include\s+/usr/share/quilt/' ],
- [ 'ruby-pkg-tools' => qr'^include\s+/usr/share/ruby-pkg-tools/1/class/' ],
- [ 'r-base-dev' => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
- [ $PYTHON_DEPEND => qr'/usr/share/cdbs/1/class/python-distutils\.mk', 'missing-python-build-dependency' ],
-);
-
-# These are similar, but the resulting dependency is only allowed, not
-# required.
-#
-# The xsfclean rule is specific to the packages maintained by the X Strike
-# Force, but there are enough of those to make the rule worthwhile.
-my @GLOBAL_CLEAN_ALLOWED = (
- [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/dpatch\.mk' ],
- [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/patchsys-quilt\.mk' ],
- [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/simple-patchsys\.mk' ],
- [ 'python-central' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pycentral' ],
- [ 'python-support' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pysupport' ],
- [ 'python-setuptools' => qr'/usr/share/cdbs/1/class/python-distutils\.mk' ],
- [ quilt => qr'^clean:\s+xsfclean\b' ],
-);
-
-# A list of packages; regular expressions that, if they match anywhere in the
-# debian/rules file, this package must be listed in either Build-Depends or
-# Build-Depends-Indep as appropriate; and optional tags as above.
-my @GLOBAL_DEPENDS = (
- [ $PYTHON_DEPEND => qr'^\t\s*dh_python\s', 'missing-dh_python-build-dependency' ],
- [ 'python-central' => qr'^\t\s*dh_pycentral\s' ],
- [ 'python-support' => qr'^\t\s*dh_pysupport\s' ],
- [ 'python-central' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pycentral' ],
- [ 'python-support' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pysupport' ],
-);
-
-# Similarly, this list of packages, regexes, and optional tags say that if the
-# regex matches in one of clean, build-arch, binary-arch, or a rule they
-# depend on, this package is allowed (and required) in Build-Depends.
-my @RULE_CLEAN_DEPENDS = (
- [ ant => qr'^\t\s*(\S+=\S+\s+)*ant\s' ],
- [ debhelper => qr'^\t\s*dh_.+' ],
- [ dpatch => qr'^\t\s*(\S+=\S+\s+)*dpatch\s' ],
- [ "po-debconf" => qr'^\t\s*debconf-updatepo\s' ],
- [ $PYTHON_DEPEND => qr'^\t\s*python\s', 'missing-python-build-dependency' ],
- [ $PYTHON_DEPEND => qr'\ssetup\.py\b', 'missing-python-build-dependency' ],
- [ 'quilt (>= 0.46-7~)' => qr'\t\s*dh_quilt_.+' ],
- [ quilt => qr'^\t\s*(\S+=\S+\s+)*quilt\s' ],
- [ yada => qr'^\t\s*yada\s' ],
-);
-
-# Similar, but the resulting dependency is only allowed, not required. We
-# permit a versioned dependency on perl-base because that used to be the
-# standard suggested dependency. No package should be depending on just
-# perl-base, since it's Priority: required.
-my @RULE_CLEAN_ALLOWED = (
- [ patch => q'^\t\s*(?:perl debian/)?yada\s+unpatch' ],
- [ 'perl | perl-base (>= 5.6.0-16)' => qr'(^\t|\|\|)\s*(perl|\$\(PERL\))\s' ],
- [ 'perl-modules (>= 5.10) | libmodule-build-perl' => qr'(^\t|\|\|)\s*(perl|\$\(PERL\))\s+Build\b' ],
- [ 'python-setuptools' => qr'\ssetup\.py\b' ],
-);
-
-# A simple list of regular expressions which, if they match anywhere in
-# debian/rules, indicate the requirements for debian/rules clean are complex
-# enough that we can't know what packages are permitted in Build-Depends and
-# should bypass the build-depends-without-arch-dep check completely.
-my @GLOBAL_CLEAN_BYPASS = (
- qr'^include\s*/usr/share/cdbs/1/class/ant\.mk',
- qr'^\s+(\S+=\S+\s+)*dh\s+'
-);
-
# Mapping of package names to section names
my @NAME_SECTION_MAPPINGS = (
[ qr/-docs?$/ => 'doc' ],
@@ -722,71 +630,6 @@ if ($type eq "source") {
}
}
- # Search through rules and determine which dependencies are required.
- # The keys in %needed and %needed_clean are the dependencies; the
- # values are the tags to use or the empty string to use the default
- # tag.
- my (%needed, %needed_clean, %allowed_clean, $bypass_needed_clean);
- open (RULES, '<', "debfiles/rules")
- or fail("cannot read debfiles/rules: $!");
- my $target = "none";
- my @rules = qw(clean binary-arch build-arch);
- my $maybe_skipping;
- while (<RULES>) {
- if (/^ifn?(eq|def)\s/) {
- $maybe_skipping++;
- } elsif (/^endif\s/) {
- $maybe_skipping--;
- }
- for my $rule (@GLOBAL_CLEAN_DEPENDS) {
- if ($_ =~ /$rule->[1]/) {
- if ($maybe_skipping) {
- $allowed_clean{$rule->[0]} = 1;
- } else {
- $needed_clean{$rule->[0]} = $rule->[2] || $needed_clean{$rule->[0]} || '';
- }
- }
- }
- for my $rule (@GLOBAL_CLEAN_ALLOWED) {
- if ($_ =~ /$rule->[1]/) {
- $allowed_clean{$rule->[0]} = 1;
- }
- }
- for my $rule (@GLOBAL_CLEAN_BYPASS) {
- if ($_ =~ /$rule/) {
- $bypass_needed_clean = 1;
- }
- }
- for my $rule (@GLOBAL_DEPENDS) {
- if ($_ =~ /$rule->[1]/ && !$maybe_skipping) {
- $needed{$rule->[0]} = $rule->[2] || $needed{$rule->[0]} || '';
- }
- }
- if (/^(\S+?):+(.*)/) {
- $target = $1;
- if (grep ($_ eq $target, @rules)) {
- push (@rules, split (' ', $2));
- }
- }
- if (grep ($_ eq $target, @rules)) {
- for my $rule (@RULE_CLEAN_DEPENDS) {
- if ($_ =~ /$rule->[1]/) {
- if ($maybe_skipping) {
- $allowed_clean{$rule->[0]} = 1;
- } else {
- $needed_clean{$rule->[0]} = $rule->[2] || $needed_clean{$rule->[0]} || '';
- }
- }
- }
- for my $rule (@RULE_CLEAN_ALLOWED) {
- if ($_ =~ /$rule->[1]/) {
- $allowed_clean{$rule->[0]} = 1;
- }
- }
- }
- }
- close RULES;
-
tag "build-depends-indep-without-arch-indep", ""
if (defined $info->field('build-depends-indep') && $arch_indep_packages == 0);
@@ -873,73 +716,6 @@ if ($type eq "source") {
}
}
- # Make sure that all the required build dependencies are there. Don't
- # issue missing-build-dependency errors for debhelper, since there's
- # another test that does that and it would just be a duplicate.
- my $build_regular = $info->relation('build-depends');
- my $build_indep = $info->relation('build-depends-indep');
- for my $package (keys %needed_clean) {
- my $tag = $needed_clean{$package} || 'missing-build-dependency';
- unless ($build_regular->implies($package)) {
- if ($build_indep->implies($package)) {
- tag "clean-should-be-satisfied-by-build-depends", $package;
- } else {
- if ($tag eq 'missing-build-dependency') {
- tag $tag, $package if $package ne 'debhelper';
- } else {
- tag $tag;
- }
- }
- }
- }
- my $noarch = $info->relation_noarch('build-depends-all');
- for my $package (keys %needed) {
- my $tag = $needed{$package} || 'missing-build-dependency';
-
- # dh_python deactivates itself if the new Python build policy
- # is enabled.
- if ($tag eq 'missing-dh_python-build-dependency') {
- next if -f 'debfiles/pycomat';
- next if defined $info->field('python-version');
- }
- unless ($noarch->implies($package)) {
- if ($tag eq 'missing-build-dependency') {
- tag $tag, $package;
- } else {
- tag $tag;
- }
- }
- }
-
- # This check is a bit tricky. We want to allow in Build-Depends a
- # dependency with any version, since reporting this tag over version
- # mismatches would be confusing and quite likely wrong. The approach
- # taken is to strip the version information off all dependencies
- # allowed in Build-Depends, strip the version information off of the
- # dependencies in Build-Depends, and then allow any dependency in
- # Build-Depends that's implied by the dependencies we require or allow
- # there.
- #
- # We also have to map | to , when building the list of allowed
- # packages so that the implications will work properly.
- #
- # This is confusing. There should be a better way to do this.
- if (defined $info->field('build-depends') && $arch_dep_packages == 0 && !$bypass_needed_clean) {
- my $build_depends = $info->field('build-depends');
- my @packages = split /\s*,\s*/, $build_depends;
- my @allowed = map { s/\([^\)]+\)//g; s/\|/,/g; $_ } keys (%needed_clean), keys (%allowed_clean);
- my $dep = Lintian::Relation->new_noarch(join(',', @allowed));
- foreach my $pkg (@packages) {
- my $name = $pkg;
- $name =~ s/[\[\(][^\)\]]+[\)\]]//g;
- $name =~ s/\s+$//;
- $name =~ s/\s+/ /g;
- unless ($dep->implies($name)) {
- tag "build-depends-without-arch-dep", $name;
- }
- }
- }
-
my (@arch_dep_pkgs, @dbg_pkgs);
foreach my $binpkg (keys %$binpkgs) {
if ($binpkg =~ m/-dbg$/) {
diff --git a/checks/fields.desc b/checks/fields.desc
index 2b02602..ed33777 100644
--- a/checks/fields.desc
+++ b/checks/fields.desc
@@ -597,67 +597,6 @@ Ref: policy 7.7
Info: The control file specifies source relations for architecture-independent
packages, but no architecture-independent packages are built.
-Tag: build-depends-without-arch-dep
-Severity: minor
-Certainty: possible
-Ref: policy 7.7
-Info: The control file lists the given package in Build-Depends, but no
- architecture-dependent packages are built. If all the packages built are
- architecture-independent, the only packages that should be listed in
- Build-Depends are those required to run the clean target (such as
- debhelper if you use dh_clean). Other build dependencies should be listed
- in Build-Depends-Indep instead.
-
-Tag: clean-should-be-satisfied-by-build-depends
-Severity: important
-Certainty: certain
-Ref: policy 7.7
-Info: The specified package is required to run the clean target of
- <tt>debian/rules</tt> and therefore must be listed in Build-Depends, not
- Build-Depends-Indep, even if no architecture-dependent packages are
- built.
-
-Tag: missing-build-dependency
-Severity: important
-Certainty: certain
-Ref: policy 4.2
-Info: The package doesn't specify a build dependency on a package that is
- used in <tt>debian/rules</tt>.
- .
- lintian intentionally does not take into account transitive dependencies.
- Even if the package build-depends on some package that in turn
- depends on the needed package, an explicit build dependency should
- be added. Otherwise, a latent bug is created that will appear without
- warning if the other package is ever updated to change its dependencies.
- Even if this seems unlikely, please always add explicit build
- dependencies on every non-essential, non-build-essential package that is
- used directly during the build.
-
-Tag: missing-python-build-dependency
-Severity: important
-Certainty: certain
-Ref: policy 4.2
-Info: The package appears to use Python as part of its build process in
- <tt>debian/rules</tt> but doesn't depend on Python.
- .
- Normally, packages that use Python as part of the build process should
- build-depend on one of python, python-all, python-dev, or python-all-dev
- depending on whether they support multiple versions of Python and whether
- they're building modules or only using Python as part of the package
- build process. Packages that depend on a specific version of Python may
- build-depend on the appropriate pythonX.Y or pythonX.Y-dev package
- instead.
-
-Tag: missing-dh_python-build-dependency
-Severity: important
-Certainty: certain
-Ref: dh_python(1)
-Info: The package runs dh_python in <tt>debian/rules</tt> but doesn't
- build-depend on python or python-dev. dh_python requires
- <tt>/usr/bin/python</tt> to run, so packages using dh_python must
- build-depend on python (or python-dev or python-all-dev, which in turn
- depend on python), even if they don't otherwise need Python to build.
-
Tag: build-conflicts-with-build-dependency
Severity: important
Certainty: certain
diff --git a/checks/rules b/checks/rules
index a598f64..f4c47c4 100644
--- a/checks/rules
+++ b/checks/rules
@@ -18,6 +18,103 @@ use strict;
use Tags;
use Util;
+# The allowed Python dependencies currently. This is the list of alternatives
+# that, either directly or through transitive dependencies that can be relied
+# upon, ensure /usr/bin/python will exist for the use of dh_python.
+our $PYTHON_DEPEND = 'python | python-dev | python-all | python-all-dev | '
+ . join (' | ', map { "python$_ | python$_-dev" } qw(2.4 2.5));
+
+# Certain build tools must be listed in Build-Depends even if there are no
+# arch-specific packages because they're required in order to run the clean
+# rule. (See Policy 7.6.) The following is a list of package dependencies;
+# regular expressions that, if they match anywhere in the debian/rules file,
+# say that this package is allowed (and required) in Build-Depends; and
+# optional tags to use for reporting the problem if some information other
+# than the default is required.
+our @GLOBAL_CLEAN_DEPENDS =
+ (
+ [ ant => qr'^include\s*/usr/share/cdbs/1/rules/ant\.mk' ],
+ [ cdbs => qr'^include\s+/usr/share/cdbs/' ],
+ [ cdbs => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
+ [ dbs => qr'^include\s+/usr/share/dbs/' ],
+ [ 'dh-make-php' => qr'^include\s+/usr/share/cdbs/1/class/pear\.mk' ],
+ [ debhelper => qr'^include\s+/usr/share/cdbs/1/rules/debhelper\.mk' ],
+ [ debhelper => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
+ [ dpatch => qr'^include\s+/usr/share/cdbs/1/rules/dpatch\.mk' ],
+ [ 'gnome-pkg-tools' => qr'^include\s+/usr/share/gnome-pkg-tools/' ],
+ [ quilt => qr'^include\s+/usr/share/cdbs/1/rules/patchsys-quilt\.mk' ],
+ [ dpatch => qr'^include\s+/usr/share/dpatch/' ],
+ [ quilt => qr'^include\s+/usr/share/quilt/' ],
+ [ 'ruby-pkg-tools' => qr'^include\s+/usr/share/ruby-pkg-tools/1/class/' ],
+ [ 'r-base-dev' => qr'^include\s+/usr/share/R/debian/r-cran\.mk' ],
+ [ $PYTHON_DEPEND => qr'/usr/share/cdbs/1/class/python-distutils\.mk', 'missing-python-build-dependency' ],
+ );
+
+# These are similar, but the resulting dependency is only allowed, not
+# required.
+#
+# The xsfclean rule is specific to the packages maintained by the X Strike
+# Force, but there are enough of those to make the rule worthwhile.
+my @GLOBAL_CLEAN_ALLOWED = (
+ [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/dpatch\.mk' ],
+ [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/patchsys-quilt\.mk' ],
+ [ patchutils => qr'^include\s+/usr/share/cdbs/1/rules/simple-patchsys\.mk' ],
+ [ 'python-central' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pycentral' ],
+ [ 'python-support' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pysupport' ],
+ [ 'python-setuptools' => qr'/usr/share/cdbs/1/class/python-distutils\.mk' ],
+ [ quilt => qr'^clean:\s+xsfclean\b' ],
+);
+
+# A list of packages; regular expressions that, if they match anywhere in the
+# debian/rules file, this package must be listed in either Build-Depends or
+# Build-Depends-Indep as appropriate; and optional tags as above.
+my @GLOBAL_DEPENDS =
+ (
+ [ $PYTHON_DEPEND => qr'^\t\s*dh_python\s', 'missing-dh_python-build-dependency' ],
+ [ 'python-central' => qr'^\t\s*dh_pycentral\s' ],
+ [ 'python-support' => qr'^\t\s*dh_pysupport\s' ],
+ [ 'python-central' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pycentral' ],
+ [ 'python-support' => qr'^DEB_PYTHON_SYSTEM\s*:?=\s*pysupport' ],
+ );
+
+# Similarly, this list of packages, regexes, and optional tags say that if the
+# regex matches in one of clean, build-arch, binary-arch, or a rule they
+# depend on, this package is allowed (and required) in Build-Depends.
+my @RULE_CLEAN_DEPENDS =
+ (
+ [ ant => qr'^\t\s*(\S+=\S+\s+)*ant\s' ],
+ [ debhelper => qr'^\t\s*dh_.+' ],
+ [ dpatch => qr'^\t\s*(\S+=\S+\s+)*dpatch\s' ],
+ [ "po-debconf" => qr'^\t\s*debconf-updatepo\s' ],
+ [ $PYTHON_DEPEND => qr'^\t\s*python\s', 'missing-python-build-dependency' ],
+ [ $PYTHON_DEPEND => qr'\ssetup\.py\b', 'missing-python-build-dependency' ],
+ [ 'quilt (>= 0.46-7~)' => qr'\t\s*dh_quilt_.+' ],
+ [ quilt => qr'^\t\s*(\S+=\S+\s+)*quilt\s' ],
+ [ yada => qr'^\t\s*yada\s' ],
+ );
+
+# Similar, but the resulting dependency is only allowed, not required. We
+# permit a versioned dependency on perl-base because that used to be the
+# standard suggested dependency. No package should be depending on just
+# perl-base, since it's Priority: required.
+my @RULE_CLEAN_ALLOWED =
+ (
+ [ patch => q'^\t\s*(?:perl debian/)?yada\s+unpatch' ],
+ [ 'perl | perl-base (>= 5.6.0-16)' => qr'(^\t|\|\|)\s*(perl|\$\(PERL\))\s' ],
+ [ 'perl-modules (>= 5.10) | libmodule-build-perl' => qr'(^\t|\|\|)\s*(perl|\$\(PERL\))\s+Build\b' ],
+ [ 'python-setuptools' => qr'\ssetup\.py\b' ],
+ );
+
+# A simple list of regular expressions which, if they match anywhere in
+# debian/rules, indicate the requirements for debian/rules clean are complex
+# enough that we can't know what packages are permitted in Build-Depends and
+# should bypass the build-depends-without-arch-dep check completely.
+my @GLOBAL_CLEAN_BYPASS =
+ (
+ qr'^include\s*/usr/share/cdbs/1/class/ant\.mk',
+ qr'^\s+(\S+=\S+\s+)*dh\s+'
+ );
+
# The following targets are required per Policy.
my %required = map { $_ => 1 }
qw(build binary binary-arch binary-indep clean);
@@ -62,6 +159,11 @@ my $start = <RULES>;
tag "debian-rules-not-a-makefile", ""
unless $start =~ m%^\#!\s*/usr/bin/make\s+-[re]?f[re]?\s*$%;
+# Holds which dependencies are required. The keys in %needed and
+# %needed_clean are the dependencies; the values are the tags to use or the
+# empty string to use the default tag.
+my (%needed, %needed_clean, %allowed_clean, $bypass_needed_clean);
+
# Scan debian/rules. We would really like to let make do this for us, but
# unfortunately there doesn't seem to be a way to get make to syntax-check and
# analyze a makefile without running at least $(shell) commands.
@@ -72,9 +174,11 @@ tag "debian-rules-not-a-makefile", ""
my $includes = 0;
my %seen;
local $_;
+my @arch_rules = (qr/^clean$/, qr/^binary-arch$/, qr/^build-arch$/);
my @current_targets;
my %rules_per_target;
my $debhelper_group;
+my $maybe_skipping;
while (<RULES>) {
next if /^\s*\#/;
$includes = 1 if m/^ *[s-]?include\s+/;
@@ -94,10 +198,45 @@ while (<RULES>) {
/^\t\s*(?:\$[\(\{]MAKE[\}\)]|make)\s(?:.*\s)?-\w*i.*(?:dist)?clean/) {
tag "debian-rules-ignores-make-clean-error", "line $.";
}
- if (/$[\(\{]DEB_BUILD_OPTS[\)\}]/) {
+ if (/\$[\(\{]DEB_BUILD_OPTS[\)\}]/) {
tag "debian-rules-uses-DEB_BUILD_OPTS", "line $.";
}
+ # Keep track of whether this portion of debian/rules may be optional
+ if (/^ifn?(eq|def)\s/) {
+ $maybe_skipping++;
+ } elsif (/^endif\s/) {
+ $maybe_skipping--;
+ }
+
+ # Check for strings anywhere in debian/rules that have implications for
+ # our dependencies.
+ for my $rule (@GLOBAL_CLEAN_DEPENDS) {
+ if (/$rule->[1]/) {
+ if ($maybe_skipping) {
+ $allowed_clean{$rule->[0]} = 1;
+ } else {
+ $needed_clean{$rule->[0]}
+ = $rule->[2] || $needed_clean{$rule->[0]} || '';
+ }
+ }
+ }
+ for my $rule (@GLOBAL_CLEAN_ALLOWED) {
+ if (/$rule->[1]/) {
+ $allowed_clean{$rule->[0]} = 1;
+ }
+ }
+ for my $rule (@GLOBAL_CLEAN_BYPASS) {
+ if (/$rule/) {
+ $bypass_needed_clean = 1;
+ }
+ }
+ for my $rule (@GLOBAL_DEPENDS) {
+ if (/$rule->[1]/ && !$maybe_skipping) {
+ $needed{$rule->[0]} = $rule->[2] || $needed{$rule->[0]} || '';
+ }
+ }
+
# Listing a rule as a dependency of .PHONY is sufficient to make it
# present for the purposes of GNU make and therefore the Policy
# requirement.
@@ -108,17 +247,24 @@ while (<RULES>) {
}
}
- if (/^([^\s:][^:]*):/) {
+ if (/^([^\s:][^:]*):+(.*)/) {
@current_targets = split (' ', $1);
- for (@current_targets) {
- if (m/%/) {
- my $pattern = quotemeta $_;
+ my @depends = map {
+ s/\$\([^\):]+:([^=]+)=([^\)]+)\1\)/$2.*/g;
+ qr/^$_$/;
+ } split (' ', $2);
+ for my $target (@current_targets) {
+ if ($target =~ /%/) {
+ my $pattern = quotemeta $target;
$pattern =~ s/\\%/.*/g;
- for my $target (keys %required) {
- $seen{$target}++ if $target =~ m/$pattern/;
+ for my $required (keys %required) {
+ $seen{$required}++ if $required =~ m/$pattern/;
}
} else {
- $seen{$_}++ if $required{$_};
+ $seen{$target}++ if $required{$target};
+ }
+ if (grep { $target =~ /$_/ } @arch_rules) {
+ push (@arch_rules, @depends);
}
}
$debhelper_group = 0;
@@ -133,9 +279,28 @@ while (<RULES>) {
# targets and check whether debhelper programs are called in a
# reasonable order.
if (m/^\s+[^\#]/) {
- foreach my $target (@current_targets) {
- $rules_per_target{$target} ||= [];
- push @{$rules_per_target{$target}}, $_;
+ my $arch = 0;
+ for my $target (@current_targets) {
+ $rules_per_target{$target} ||= [];
+ push @{$rules_per_target{$target}}, $_;
+ $arch = 1 if (grep { $target =~ /$_/ } @arch_rules);
+ }
+ if ($arch) {
+ for my $rule (@RULE_CLEAN_DEPENDS) {
+ if (/$rule->[1]/) {
+ if ($maybe_skipping) {
+ $allowed_clean{$rule->[0]} = 1;
+ } else {
+ $needed_clean{$rule->[0]}
+ = $rule->[2] || $needed_clean{$rule->[0]} || '';
+ }
+ }
+ }
+ for my $rule (@RULE_CLEAN_ALLOWED) {
+ if (/$rule->[1]/) {
+ $allowed_clean{$rule->[0]} = 1;
+ }
+ }
}
if (m/^\s+(dh_\S+)\b/ and $debhelper_order{$1}) {
my $command = $1;
@@ -173,7 +338,84 @@ if ($architecture eq "all" && scalar @{$rules_per_target{'binary-arch'}}) {
}
tag "binary-arch-rules-but-pkg-is-arch-indep" if $nonempty;
}
+
+# Make sure that all the required build dependencies are there. Don't
+# issue missing-build-dependency errors for debhelper, since there's
+# another test that does that and it would just be a duplicate.
+my $build_regular = $info->relation('build-depends');
+my $build_indep = $info->relation('build-depends-indep');
+for my $package (keys %needed_clean) {
+ my $tag = $needed_clean{$package} || 'missing-build-dependency';
+ unless ($build_regular->implies($package)) {
+ if ($build_indep->implies($package)) {
+ tag "clean-should-be-satisfied-by-build-depends", $package;
+ } else {
+ if ($tag eq 'missing-build-dependency') {
+ tag $tag, $package if $package ne 'debhelper';
+ } else {
+ tag $tag;
+ }
+ }
+ }
}
+my $noarch = $info->relation_noarch('build-depends-all');
+for my $package (keys %needed) {
+ my $tag = $needed{$package} || 'missing-build-dependency';
+
+ # dh_python deactivates itself if the new Python build policy is enabled.
+ if ($tag eq 'missing-dh_python-build-dependency') {
+ next if -f 'debfiles/pycomat';
+ next if defined $info->field('python-version');
+ }
+ unless ($noarch->implies($package)) {
+ if ($tag eq 'missing-build-dependency') {
+ tag $tag, $package;
+ } else {
+ tag $tag;
+ }
+ }
+}
+
+# This check is a bit tricky. We want to allow in Build-Depends a dependency
+# with any version, since reporting this tag over version mismatches would be
+# confusing and quite likely wrong. The approach taken is to strip the
+# version information off all dependencies allowed in Build-Depends, strip the
+# version information off of the dependencies in Build-Depends, and then allow
+# any dependency in Build-Depends that's implied by the dependencies we
+# require or allow there.
+#
+# We also have to map | to , when building the list of allowed packages so
+# that the implications will work properly.
+#
+# This is confusing. There should be a better way to do this.
+my $arch_dep_packages = 0;
+for my $binpkg (keys %{ $info->binaries } ) {
+ my $arch = $info->binary_field($binpkg, 'architecture');
+ $arch_dep_packages++ unless ($arch eq 'all');
+}
+if (defined $info->field('build-depends') and $arch_dep_packages == 0
+ and not $bypass_needed_clean) {
+ my $build_depends = $info->field('build-depends');
+ my @packages = split /\s*,\s*/, $build_depends;
+ my @allowed = map {
+ s/\([^\)]+\)//g;
+ s/\|/,/g;
+ $_
+ } keys (%needed_clean), keys (%allowed_clean);
+ my $dep = Lintian::Relation->new_noarch(join(',', @allowed));
+ for my $pkg (@packages) {
+ my $name = $pkg;
+ $name =~ s/[\[\(][^\)\]]+[\)\]]//g;
+ $name =~ s/\s+$//;
+ $name =~ s/\s+/ /g;
+ unless ($dep->implies($name)) {
+ tag "build-depends-without-arch-dep", $name;
+ }
+ }
+}
+
+}
+
1;
# Local Variables:
diff --git a/checks/rules.desc b/checks/rules.desc
index 6c36658..59ebd93 100644
--- a/checks/rules.desc
+++ b/checks/rules.desc
@@ -2,7 +2,7 @@ Check-Script: rules
Author: Russ Allbery <rra@debian.org>
Type: source
Unpack-Level: 1
-Needs-Info: debfiles
+Needs-Info: debfiles, source-control-file
Info: Check targets and actions in debian/rules.
Abbrev: rul
@@ -101,3 +101,64 @@ Info: One of the targets in the <tt>debian/rules</tt> file for this
dh_shlibdeps should be called before dh_gencontrol, and all should be
called before dh_builddeb. Calling them in the wrong order may cause
incorrect or missing package files and metadata.
+
+Tag: missing-build-dependency
+Severity: important
+Certainty: certain
+Ref: policy 4.2
+Info: The package doesn't specify a build dependency on a package that is
+ used in <tt>debian/rules</tt>.
+ .
+ lintian intentionally does not take into account transitive dependencies.
+ Even if the package build-depends on some package that in turn
+ depends on the needed package, an explicit build dependency should
+ be added. Otherwise, a latent bug is created that will appear without
+ warning if the other package is ever updated to change its dependencies.
+ Even if this seems unlikely, please always add explicit build
+ dependencies on every non-essential, non-build-essential package that is
+ used directly during the build.
+
+Tag: missing-python-build-dependency
+Severity: important
+Certainty: certain
+Ref: policy 4.2
+Info: The package appears to use Python as part of its build process in
+ <tt>debian/rules</tt> but doesn't depend on Python.
+ .
+ Normally, packages that use Python as part of the build process should
+ build-depend on one of python, python-all, python-dev, or python-all-dev
+ depending on whether they support multiple versions of Python and whether
+ they're building modules or only using Python as part of the package
+ build process. Packages that depend on a specific version of Python may
+ build-depend on the appropriate pythonX.Y or pythonX.Y-dev package
+ instead.
+
+Tag: missing-dh_python-build-dependency
+Severity: important
+Certainty: certain
+Ref: dh_python(1)
+Info: The package runs dh_python in <tt>debian/rules</tt> but doesn't
+ build-depend on python or python-dev. dh_python requires
+ <tt>/usr/bin/python</tt> to run, so packages using dh_python must
+ build-depend on python (or python-dev or python-all-dev, which in turn
+ depend on python), even if they don't otherwise need Python to build.
+
+Tag: build-depends-without-arch-dep
+Severity: minor
+Certainty: possible
+Ref: policy 7.7
+Info: The control file lists the given package in Build-Depends, but no
+ architecture-dependent packages are built. If all the packages built are
+ architecture-independent, the only packages that should be listed in
+ Build-Depends are those required to run the clean target (such as
+ debhelper if you use dh_clean). Other build dependencies should be listed
+ in Build-Depends-Indep instead.
+
+Tag: clean-should-be-satisfied-by-build-depends
+Severity: important
+Certainty: certain
+Ref: policy 7.7
+Info: The specified package is required to run the clean target of
+ <tt>debian/rules</tt> and therefore must be listed in Build-Depends, not
+ Build-Depends-Indep, even if no architecture-dependent packages are
+ built.
diff --git a/debian/changelog b/debian/changelog
index 4e46d31..3af203b 100755
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,7 +1,15 @@
lintian (2.2.14) unstable; urgency=low
- * checks/fields:
+ * checks/fields{,.desc}
+ [FL] packages named lib*-camlp4-dev should be in section ocaml
+ + [RA] Move debian/rules parsing to check build dependencies to
+ checks/rules.
+ * checks/rules{,.desc}:
+ + [RA] Moved checking of build dependencies based on programs invoked
+ in debian/rules from checks/fields to here.
+ + [RA] Expand Lintian's understanding of which targets are run for the
+ clean target to include targets invoked via pattern variable
+ expansion. (Closes: #536405)
* lib/Spelling.pm:
+ [RA] Add spelling correction for precedence.
diff --git a/t/tests/debhelper-dh-clean-k-ok/debian/debian/control.in b/t/tests/rules-build-dep-pattern/debian/debian/control.in
similarity index 91%
copy from t/tests/debhelper-dh-clean-k-ok/debian/debian/control.in
copy to t/tests/rules-build-dep-pattern/debian/debian/control.in
index 76b52f1..85d12ac 100644
--- a/t/tests/debhelper-dh-clean-k-ok/debian/debian/control.in
+++ b/t/tests/rules-build-dep-pattern/debian/debian/control.in
@@ -3,7 +3,7 @@ Priority: extra
Section: {$section}
Maintainer: {$author}
Standards-Version: {$standards_version}
-Build-Depends: debhelper (>= 6)
+Build-Depends: debhelper (>= 7), python
Package: {$srcpkg}
Architecture: {$architecture}
diff --git a/t/tests/rules-dh-unused-target-nonempty/debian/debian/rules b/t/tests/rules-build-dep-pattern/debian/debian/rules
similarity index 59%
copy from t/tests/rules-dh-unused-target-nonempty/debian/debian/rules
copy to t/tests/rules-build-dep-pattern/debian/debian/rules
index bb4437f..b0d1e14 100755
--- a/t/tests/rules-dh-unused-target-nonempty/debian/debian/rules
+++ b/t/tests/rules-build-dep-pattern/debian/debian/rules
@@ -5,8 +5,17 @@ build-stamp:
dh build
touch $@
-clean:
- dh $@
+# From deejayd 0.8.2-1
+clean: $(PYVERS:%=clean-python%)
+
+clean-python%:
+ dh_testdir
+ dh_testroot
+
+ rm -f build-python*
+ python$* setup.py clean --all
+ find $(CURDIR) -name '*pyc' -exec rm -f {} \;
+ dh_clean
install: install-stamp
install-stamp: build-stamp
@@ -15,12 +24,9 @@ install-stamp: build-stamp
binary-arch: install
dh $@
- # This target is not empty, but it should be
- -install foo bar
binary-indep: install
dh $@
binary: binary-arch binary-indep
-
.PHONY: binary binary-arch binary-indep install clean build
diff --git a/t/tests/rules-build-dep-pattern/desc b/t/tests/rules-build-dep-pattern/desc
new file mode 100644
index 0000000..5d2d48d
--- /dev/null
+++ b/t/tests/rules-build-dep-pattern/desc
@@ -0,0 +1,6 @@
+Testname: rules-build-dep-pattern
+Sequence: 6000
+Version: 1.0
+Description: Check recognition of pattern dependencies
+Test-Against: build-depends-without-arch-dep
+References: Bug#536405
diff --git a/t/debs/deb-format-record-size/tags b/t/tests/rules-build-dep-pattern/tags
similarity index 100%
copy from t/debs/deb-format-record-size/tags
copy to t/tests/rules-build-dep-pattern/tags
--
Debian package checker
Reply to: