[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

lintian: r1113 - in trunk: checks debian testset testset/scripts testset/scripts/debian



Author: rra
Date: 2008-01-05 06:57:31 +0100 (Sat, 05 Jan 2008)
New Revision: 1113

Added:
   trunk/testset/scripts/jruby-broken
   trunk/testset/scripts/sh-broken
Modified:
   trunk/checks/scripts
   trunk/checks/scripts.desc
   trunk/debian/changelog
   trunk/testset/scripts/debian/rules
   trunk/testset/tags.scripts
Log:
* checks/scripts{.desc,}:
  + [RA] Rewrite script path and dependency checking.  Remove scripts
    and packages no longer in the archive.  Add new versions of
    versioned scripts and packages.  Fix the dependencies for pike
    interpreters.  (Closes: #458896)
  + [RA] Reformat long descriptions and collapse some tags.
  + [RA] For consistent results, only syntax-check sh and bash scripts.
    Also ignore all dpatch files, not just those in /usr/src.

Modified: trunk/checks/scripts
===================================================================
--- trunk/checks/scripts	2008-01-05 05:51:39 UTC (rev 1112)
+++ trunk/checks/scripts	2008-01-05 05:57:31 UTC (rev 1113)
@@ -28,170 +28,145 @@
 use Tags;
 use Util;
 
-sub run {
+# This is a map of all known interpreters.  The key is the interpreter name
+# (the binary invoked on the #! line).  The value is an anonymous array of one
+# or two elements.  The first, mandatory argument is the path on a Debian
+# system where that interpreter would be installed.  The second, optional
+# argument is the dependency that provides that interpreter.  If the second
+# argument isn't given, the package name is assumed to be the same as the
+# interpreter name.  (Saves some typing.)
+#
+# Some interpreters list empty dependencies (as opposed to undefined ones).
+# Those interpreters should not have any dependency for one reason or another
+# (usually because they're essential packages or aren't used in a normal way).
+#
+# Do not list versioned patterns here (such as pythonX.Y, rubyX.Y, etc.).  For
+# those, see %versioned_interpreters below.
+our %interpreters =
+    (ash	    => [ '/bin' ],
+     awk	    => [ '/usr/bin', '' ],
+     bash	    => [ '/bin', '' ],
+     bltwish	    => [ '/usr/bin', 'blt' ],
+     csh	    => [ '/bin', 'tcsh | csh | c-shell' ],
+     dash	    => [ '/bin' ],
+     expect	    => [ '/usr/bin' ],
+     expectk	    => [ '/usr/bin' ],
+     fish	    => [ '/usr/bin' ],
+     gawk	    => [ '/usr/bin' ],
+     gbr2	    => [ '/usr/bin', 'gambas2-runtime' ],
+     gbx	    => [ '/usr/bin', 'gambas-runtime' ],
+     gbx2	    => [ '/usr/bin', 'gambas2-runtime' ],
+     gforth	    => [ '/usr/bin' ],
+     gnuplot	    => [ '/usr/bin' ],
+     gosh	    => [ '/usr/bin', 'gauche' ],
+     'install-menu' => [ '/usr/bin', '' ],
+     jed	    => [ '/usr/bin' ],
+     'jed-script'   => [ '/usr/bin', 'jed | xjed' ],
+     ksh	    => [ '/bin', 'mksh | pdksh' ],
+     lefty	    => [ '/usr/bin', 'graphviz' ],
+     magicfilter    => [ '/usr/sbin' ],
+     make	    => [ '/usr/bin', 'make | build-essential' ],
+     mawk	    => [ '/usr/bin' ],
+     ocamlrun	    => [ '/usr/bin', 'ocaml | ocaml-base-nox' ],
+     pagsh	    => [ '/usr/bin', 'openafs-client | heimdal-clients' ],
+     parrot	    => [ '/usr/bin' ],
+     perl	    => [ '/usr/bin', '' ],
+     python	    => [ '/usr/bin', 'python | python-minimal' ],
+     pforth	    => [ '/usr/bin' ],
+     rc		    => [ '/usr/bin' ],
+     regina	    => [ '/usr/bin', 'regina-rexx' ],
+     rexx	    => [ '/usr/bin', 'regina-rexx' ],
+     ruby	    => [ '/usr/bin' ],
+     runhugs	    => [ '/usr/bin', 'hugs | hugs98' ],
+     sed	    => [ '/bin', '' ],
+     sh		    => [ '/bin', '' ],
+     slsh	    => [ '/usr/bin' ],
+     speedy	    => [ '/usr/bin', 'speedy-cgi-perl' ],
+     tcl	    => [ '/usr/bin', 'tclx8.3' ],
+     tcsh	    => [ '/usr/bin' ],
+     tixwish	    => [ '/usr/bin', 'tix' ],
+     trs	    => [ '/usr/bin', 'konwert' ],
+     xjed	    => [ '/usr/bin', 'xjed' ],
+     yforth	    => [ '/usr/bin', 'yforth' ],
+     zsh	    => [ '/bin' ],
+    );
 
-# Don't forget to edit the scripts.desc file if you change these!
+# The more complex case of interpreters that may have a version number.
+#
+# This is a hash from the base interpreter name to a list.  The base
+# interpreter name may appear by itself or followed by some combination of
+# dashes, digits, and periods.  The values are the directory in which the
+# interpreter is found, the dependency to add for a version-less interpreter,
+# a regular expression to match versioned interpreters and extract the version
+# number, the package dependency for a versioned interpreter, and the list of
+# known versions.
+#
+# An interpreter with a version must have a dependency on the specific package
+# formed by taking the fourth element of the list and replacing $1 with the
+# version number.  An interpreter without a version is rejected if the second
+# element is undef; otherwise, the package must depend on the disjunction of
+# the second argument (if non-empty) and all the packages formed by taking the
+# list of known versions (the fifth element and on) and replacing $1 in the
+# fourth argument with them.
+#
+# For example:
+#
+#    lua => [ '/usr/bin', 'lua', qr/^lua([\d.]+)$/, 'lua$1', qw(40 50 5.1) ]
+#
+# says that any lua interpreter must be in /usr/bin, a package using
+# /usr/bin/lua50 must depend on lua50, and a package using just /usr/bin/lua
+# must satisfy lua | lua40 | lusa50 | lua5.1.
+#
+# The list of known versions is the largest maintenance headache here, but
+# it's only used for the unversioned dependency handling, and then only when
+# someone uses the unversioned script but depends on a specific version for
+# some reason.  So it's not a huge problem if it's a little out of date.
+our %versioned_interpreters =
+    (guile   => [ '/usr/bin', 'guile',
+		  qr/^guile-([\d.]+)$/, 'guile-$1', qw(1.6 1.8)
+		],
+     jruby   => [ '/usr/bin', undef,
+		  qr/^jruby([\d.]+)$/, 'jruby$1', qw(0.9 1.0)
+		],
+     lua     => [ '/usr/bin', 'lua',
+		  qr/^lua([\d.]+)$/, 'lua$1', qw(40 50 5.1)
+		],
+     octave  => [ '/usr/bin', 'octave',
+		  qr/^octave([\d.]+)$/, 'octave$1', qw(2.1 2.9 3.0)
+		],
+     php     => [ '/usr/bin', '',
+		  qr/^php(\d+)$/, 'php$1-cli', qw(5)
+		],
+     pike    => [ '/usr/bin', '',
+		  qr/^pike([\d.]+)$/, 'pike$1 | pike$1-core', qw(7.6 7.7)
+		],
+     python  => [ '/usr/bin', undef,
+		  qr/^python([\d.]+)$/, 'python$1 | python$1-minimal',
+		  qw(2.4 2.5)
+		],
+     ruby    => [ '/usr/bin', undef,
+		  qr/^ruby([\d.]+)$/, 'ruby$1', qw(1.8 1.9)
+		],
+     scsh    => [ '/usr/bin', 'scsh',
+		  qr/^scsh-([\d.]+)$/, 'scsh-$1', qw(0.6)
+		],
+     tclsh   => [ '/usr/bin', 'tclsh',
+		  qr/^tclsh([\d.]+)$/, 'tcl$1', qw(8.3 8.4 8.5)
+		],
+     wish    => [ '/usr/bin', 'wish',
+		  qr/^wish([\d.]+)$/, 'tk$1', qw(8.3 8.4 8.5)
+		],
+    );
 
-my %valid_interpreters = (
-			  'ash' => '/bin/ash',
-			  'awk' => '/usr/bin/awk',
-			  'bash' => '/bin/bash',
-			  'bltwish' => '/usr/bin/bltwish',
-			  'burlap' => '/usr/bin/burlap',
-			  'csh' => '/bin/csh',
-			  'dash' => '/bin/dash',
-			  'expect' => '/usr/bin/expect',
-			  'expectk' => '/usr/bin/expectk',
-			  'fish' => '/usr/bin/fish',
-			  'gawk' => '/usr/bin/gawk',
-			  'gbr2' => '/usr/bin/gbr2',
-			  'gbx' => '/usr/bin/gbx',
-			  'gbx2' => '/usr/bin/gbx2',
-			  'gforth' => '/usr/bin/gforth',
-			  'gnuplot' => '/usr/bin/gnuplot',
-			  'gosh' => '/usr/bin/gosh',
-			  'guile' => '/usr/bin/guile',
-			  'install-menu' => '/usr/bin/install-menu',
-			  'jed' => '/usr/bin/jed',
-			  'jed-script' => '/usr/bin/jed-script',
-			  'jruby0.9' => '/usr/bin/jruby0.9',
-			  'jruby1.0' => '/usr/bin/jruby1.0',
-			  'js' => '/usr/bin/js',
-			  'kforth' => '/usr/bin/kforth',
-			  'ksh' => '/bin/ksh',
-			  'lefty' => '/usr/bin/lefty',
-			  'lua40' => '/usr/bin/lua40',
-			  'lua50' => '/usr/bin/lua50',
-			  'lua5.1' => '/usr/bin/lua5.1',
-			  'magicfilter' => '/usr/sbin/magicfilter',
-			  'make' => '/usr/bin/make',
-			  'mawk' => '/usr/bin/mawk',
-			  'nawk' => '/usr/bin/nawk',
-			  'ocaml' => '/usr/bin/ocamlrun',
-			  'ocamlrun' => '/usr/bin/ocamlrun',
-			  'octave' => '/usr/bin/octave',
-			  'pagsh' => '/usr/bin/pagsh',
-			  'parrot' => '/usr/bin/parrot',
-			  'perl' => '/usr/bin/perl',
-			  'perl-5.005' => '/usr/bin/perl-5.005',
-			  'perl-5.004' => '/usr/bin/perl-5.004',
-			  'pforth' => '/usr/bin/pforth',
-			  'php' => '/usr/bin/php',
-			  'php3' => '/usr/bin/php3',
-			  'php4' => '/usr/bin/php4',
-			  'php5' => '/usr/bin/php5',
-			  'pike' => '/usr/bin/pike',
-			  'pike7' => '/usr/bin/pike7',
-			  'pike7.6' => '/usr/bin/pike7.6',
-			  'python' => '/usr/bin/python',
-			  'python1.5' => '/usr/bin/python1.5',
-			  'python2.1' => '/usr/bin/python2.1',
-			  'python2.2' => '/usr/bin/python2.2',
-			  'python2.3' => '/usr/bin/python2.3',
-			  'python2.4' => '/usr/bin/python2.4',
-			  'python2.5' => '/usr/bin/python2.5',
-			  'rexx' => '/usr/bin/rexx',
-			  'regina' => '/usr/bin/regina',
-			  'rc' => '/usr/bin/rc',
-			  'runhugs1.4' => '/usr/bin/runhugs1.4',
-			  'runhugs98' => '/usr/bin/runhugs98',
-			  'runhugs' => '/usr/bin/runhugs',
-			  'ruby' => '/usr/bin/ruby',
-			  'ruby1.6' => '/usr/bin/ruby1.6',
-			  'ruby1.8' => '/usr/bin/ruby1.8',
-			  'ruby1.9' => '/usr/bin/ruby1.9',
-			  'scsh' => '/usr/bin/scsh',
-			  'sed' => '/bin/sed',
-			  'sh' => '/bin/sh',
-			  'slsh' => '/usr/bin/slsh',
-			  'speedy' => '/usr/bin/speedy',
-			  'tcl' => '/usr/bin/tcl',
-			  'tclsh' => '/usr/bin/tclsh',
-			  'tclsh8.3' => '/usr/bin/tclsh8.3',
-			  'tclsh8.4' => '/usr/bin/tclsh8.4',
-			  'tcsh' => '/usr/bin/tcsh',
-			  'tixwish' => '/usr/bin/tixwish',
-			  'trs' => '/usr/bin/trs',
-			  'wish' => '/usr/bin/wish',
-			  'wish8.0' => '/usr/bin/wish8.0',
-			  'wish8.3' => '/usr/bin/wish8.3',
-			  'wish8.4' => '/usr/bin/wish8.4',
-			  'xjed' => '/usr/bin/xjed',
-			  'yforth' => '/usr/bin/yforth',
-			  'zsh' => '/bin/zsh'
-			 );
-
-my %interpreter_dependencies = (
-				'ash' => 'ash',
-				'bltwish' => 'blt',
-				'burlap' => 'felt',
-				'csh' => 'c-shell | tcsh | csh',
-				'dash' => 'dash',
-				'expect' => 'expect',
-				'expectk' => 'expectk',
-				'fish' => 'fish',
-				'gawk' => 'gawk',
-				'gbr2' => 'gambas2-runtime',
-				'gbx' => 'gambas-runtime',
-				'gbx2' => 'gambas2-runtime',
-				'gforth' => 'gforth',
-				'gnuplot' => 'gnuplot',
-				'gosh' => 'gauche',
-				'guile' => 'guile',
-				'jed' => 'jed',
-				'jed-script' => 'jed | xjed',
-				'jruby0.9' => 'jruby0.9',
-				'jruby1.0' => 'jruby1.0',
-				'js' => 'ngs-js',
-				'kforth' => 'kforth',
-				'ksh' => 'pdksh',
-				'lefty' => 'graphviz',
-				'lua40' => 'lua40',
-				'lua50' => 'lua50',
-				'lua5.1' => 'lua5.1',
-				'magicfilter' => 'magicfilter',
-				'make' => 'make | build-essential',
-				'mawk' => 'mawk',
-				'ocaml' => 'ocaml',
-				'octave' => 'octave | octave2.1 | octave2.9',
-				'pagsh' => 'openafs-client | heimdal-clients',
-				'parrot' => 'parrot',
-				'perl-5.005' => 'perl-5.005',
-				'perl-5.004' => 'perl-5.004',
-				'pforth' => 'pforth',
-				'php' => 'php4-cli | php5-cli',
-				'php3' => 'php3-cgi',
-				'php4' => 'php4-cli',
-				'php5' => 'php5-cli',
-				'pike' => 'pike',
-				'pike7' => 'pike7',
-				'pike7.6' => 'pike7.6',
-				'rc' => 'rc',
-				'regina' => 'regina-rexx',
-				'rexx' => 'regina-rexx',
-				'runhugs1.4' => 'hugs',
-				'runhugs98' => 'hugs98',
-				'scsh' => 'scsh',
-				'slsh' => 'slsh',
-				'speedy' => 'speedy-cgi-perl',
-				'tcl' => 'tclx8.3',
-				'tcsh' => 'tcsh',
-				'tixwish' => 'tix',
-				'trs' => 'konwert',
-				'xjed' => 'xjed',
-				'yforth' => 'yforth',
-				'zsh' => 'zsh'
-			       );
-
 # Any of the following packages can satisfy an update-inetd dependency.
-my $update_inetd
+our $update_inetd
     = join (' | ', qw(update-inetd inet-superserver openbsd-inetd rlinetd));
 
 # Appearance of one of these regexes in a maintainer script means that there
 # must be a dependency (or pre-dependency) on the given package.  The tag
 # reported is maintainer-script-needs-depends-on-%s, so be sure to update
 # scripts.desc when adding a new rule.
-my @depends_needed = (
+our @depends_needed = (
 	[ adduser	=> '\badduser\b'	   ],
 	[ gconf2	=> '\bgconf-schemas\b'	   ],
 	[ $update_inetd	=> '\bupdate-inetd\b'	   ],
@@ -199,6 +174,8 @@
 	[ 'xml-core'	=> '\bupdate-xmlcatalog\b' ],
 );
 
+sub run {
+
 my %executable = ();
 my %suid = ();
 my %ELF = ();
@@ -235,18 +212,17 @@
 close(FILEINFO);
 
 my $all_deps = '';
-foreach my $depfield ('suggests', 'recommends', 'depends', 'pre-depends',
-		   'provides') {
-    $deps{$depfield} = '';
-    if (open(IN, '<', "fields/$depfield")) {
+for my $field (qw/suggests recommends depends pre-depends provides/) {
+    $deps{$field} = '';
+    if (open(IN, '<', "fields/$field")) {
 	$_ = join('', <IN>);
 	close(IN);
         chomp;
-        $deps{$depfield} = $_;
+        $deps{$field} = $_;
         $all_deps .= ', ' if $all_deps;
         $all_deps .= $_;
     }
-    $deps{$depfield} = Dep::parse($deps{$depfield});
+    $deps{$field} = Dep::parse($deps{$field});
 }
 $all_deps .= ', ' if $all_deps;
 $all_deps .= $pkg;
@@ -284,83 +260,62 @@
 	next;
     }
 
-    # either they use an absolute path or they call it as '/usr/bin/env interp'
+    # Either they use an absolute path or they use '/usr/bin/env interp'.
     tag("interpreter-not-absolute", $filename, "#!$interpreter")
-	       unless $is_absolute;
+	unless $is_absolute;
     tag("script-not-executable", $filename)
-	unless ($executable{$filename} or
-		$filename =~ m,usr/(lib|share)/.*\.pm, or
-		$filename =~ m,usr/(lib|share)/ruby/.*\.rb, or
-		$filename =~ m,\.in$, or
-		$filename =~ m,etc/menu-methods, or
-		$filename =~ m,etc/X11/Xsession.d,);
+	unless ($executable{$filename}
+		or $filename =~ m,usr/(lib|share)/.*\.pm,
+		or $filename =~ m,usr/(lib|share)/ruby/.*\.rb,
+		or $filename =~ m,\.in$,
+		or $filename =~ m,etc/menu-methods,
+		or $filename =~ m,etc/X11/Xsession.d,);
 
-    if (exists $valid_interpreters{$base}) {
-	unless ($interpreter eq $valid_interpreters{$base} or
-		defined $calls_env) {
-	    # save us from some copy and paste
-	    if ($base =~ /^(ruby|python)(?:\d\.\d)?$/) {
-		tag("wrong-path-for-$1", $filename, "#!$interpreter");
-	    } else {
-		tag("wrong-path-for-interpreter",
-		    "#!$interpreter != $valid_interpreters{$base}",
-		    "($filename)");
-	    }
-	}
+    # Warn about csh scripts.
+    tag("csh-considered-harmful", $filename)
+        if (($base eq 'csh' or $base eq 'tcsh')
+	    and $executable{$filename}
+	    and $filename !~ m,^./etc/csh/login.d/,);
 
-	# Do not complain about dependencies for non-executable scripts.
-	if ($executable{$filename}) {
-	    if (exists $interpreter_dependencies{$base}) {
-		my @deps = split(/,/,$interpreter_dependencies{$base});
-		if ($base eq 'php') {
-		    tag("php-script-but-no-php-cli-dep", $filename)
-			unless Dep::implies($deps{all}, Dep::parse($interpreter_dependencies{$base}));
-		} elsif ($base =~ /^(php\d?|(m|g)awk)/) {
-		    tag("$base-script-but-no-$deps[0]-dep", $filename)
-			unless Dep::implies($deps{all}, Dep::parse($interpreter_dependencies{$base}));
-		} else {
-		    tag("missing-dep-for-interpreter",
-			"$base => $deps[0]", "($filename)")
-			unless (Dep::implies($deps{all}, Dep::parse($interpreter_dependencies{$base})) ||
-			($base eq "csh" && $filename =~ m,^./etc/csh/login.d/,) ||
-			($base eq "fish" && $filename =~ m,^./etc/fish.d/,));
+    # Syntax-check most shell scripts, but don't syntax-check scripts that end
+    # in .dpatch.  bash -n doesn't stop checking at exit 0 and goes on to blow
+    # up on the patch itself.
+    if ($base =~ /^(?:(?:b|d)?a|k|z)?sh$/) {
+	if (-x "$interpreter" && ! script_is_evil_and_wrong("unpacked/$filename")) {
+	    if ($filename !~ m,\.dpatch$,) {
+		if (check_script_syntax($interpreter, "unpacked/$filename")) {
+		    tag("shell-script-fails-syntax-check", $filename);
 		}
-	    } elsif ($base =~ /^python(\d.\d)?$/) {
-		my $ver = $1 ? $1 : "";
-		tag("python-script-but-no-python-dep", $filename)
-                    unless Dep::implies($deps{all}, Dep::parse("python$ver | python${ver}-minimal"));
-	    } elsif ($base =~ /^ruby(\d.\d)?$/) {
-		my $ver = $1 ? $1 : "";
-		tag("ruby-script-but-no-ruby-dep", $filename)
-                    unless Dep::implies($deps{all}, Dep::parse("ruby$ver"));
-	    } elsif ($base eq 'perl' && $suid{$filename}) {
-		tag("suid-perl-script-but-no-perl-suid-dep", $filename)
-                    unless Dep::implies($deps{all}, Dep::parse('perl-suid'));
-	    } elsif ($base =~ m/^tclsh(\d+\.\d+)?$/) {
-		my $ver = $1 ? $1 : "";
-		if ($ver) {
-		    tag("tclsh-script-but-no-tclsh-dep", "$filename $base")
-			unless Dep::implies($deps{all}, Dep::parse("tcl$ver"));
-		} else {
-		    tag("tclsh-script-but-no-tclsh-dep", "$filename $base")
-			unless Dep::implies($deps{all}, Dep::parse("tcl8.3 | tcl8.4 | tclsh"));
-		}
-	    } elsif ($base =~ m/^wish(\d+\.\d+)?$/) {
-		my $ver = $1 ? $1 : "";
-		if ($ver) {
-		    tag("wish-script-but-no-wish-dep", "$filename $base")
-			unless Dep::implies($deps{all}, Dep::parse("tk$ver"));
-		} else {
-		    tag("wish-script-but-no-wish-dep", "$filename $base")
-			unless Dep::implies($deps{all}, Dep::parse("tk8.3 | tk8.4 | wish"));
-		}
 	    }
 	}
+    }
+
+    # Try to find the expected path of the script to check.  First check
+    # %interpreters and %versioned_interpreters.  If not found there, see if
+    # it ends in a version number and the base is found in
+    # %versioned_interpreters.
+    my $data = $interpreters{$base};
+    my $versioned = 0;
+    if (not defined $data) {
+	$data = $versioned_interpreters{$base};
+	undef $data if ($data && not defined ($data->[1]));
+	if (not defined ($data) and $base =~ /^(.*[^\d.-])-?[\d.]+$/) {
+	    $data = $versioned_interpreters{$1};
+	    undef $data unless $base =~ /$data->[2]/;
+	}
+	$versioned = 1;
+    }
+    if ($data) {
+	my $expected = $data->[0] . '/' . $base;
+	unless ($interpreter eq $expected or defined $calls_env) {
+	    tag("wrong-path-for-interpreter",
+		"#!$interpreter != $expected", "($filename)");
+	}
     } elsif ($interpreter =~ m,/usr/local/,) {
 	tag("interpreter-in-usr-local", $filename, "#!$interpreter");
-    } elsif ($executable{'.' . $interpreter}) { # each key is './path/to/exe'
-	# Package installs the interpreter itself, so it's probably ok.
-	# Don't emit any tag for this.
+    } elsif ($executable{'.' . $interpreter}) {
+	# Package installs the interpreter itself, so it's probably ok.  Don't
+	# emit any tag for this.
     } elsif ($base eq 'suidperl') {
 	tag("calls-suidperl-directly", $filename);
     } elsif ($interpreter eq '/bin/env') {
@@ -369,22 +324,63 @@
 	tag("unusual-interpreter", $filename, "#!$interpreter");
     }
 
-    tag("csh-considered-harmful", $filename)
-        if (($base eq 'csh' or $base eq 'tcsh') and $executable{$filename}
-	    and $filename !~ m,^./etc/csh/login.d/,);
-
-    # Don't syntax-check scripts in /usr/src that end in .dpatch.  bash -n
-    # doesn't stop checking at exit 0 and goes on to blow up on the patch
-    # itself.
-    if ($base =~ /^(?:(?:b|d)?a|k|z)?sh$/) {
-	if (-x "$interpreter" && ! script_is_evil_and_wrong("unpacked/$filename")) {
-	    if ($filename !~ m,^./usr/src/.*\.dpatch$,) {
-		if (check_script_syntax($interpreter, "unpacked/$filename")) {
-		    tag("shell-script-fails-syntax-check", $filename);
-		}
+    # If we found the interpreter and the script is executable, check
+    # dependencies.  This should be the last thing we do in the loop so that
+    # we can use next for an early exit and reduce the nesting.
+    next unless ($data && $executable{$filename});
+    if (!$versioned) {
+	my $depends = $data->[1];
+	if (not defined $depends) {
+	    $depends = $base;
+	}
+	if ($depends && !Dep::implies($deps{all}, Dep::parse($depends))) {
+	    if ($base =~ /^(python|ruby|(m|g)awk)$/) {
+		tag("$base-script-but-no-$base-dep", $filename);
+	    } elsif ($base eq 'csh' && $filename =~ m,^\./etc/csh/login.d/,) {
+		# Initialization files for csh.
+	    } elsif ($base eq 'fish' && $filename =~ m,^./etc/fish.d/,) {
+		# Initialization files for fish.
+	    } else {
+		tag('missing-dep-for-interpreter', "$base => $depends",
+		    "($filename)");
 	    }
 	}
-	next;
+	if ($base eq 'perl' && $suid{$filename}) {
+	    tag("suid-perl-script-but-no-perl-suid-dep", $filename)
+		unless Dep::implies($deps{all}, Dep::parse('perl-suid'));
+	}
+    } elsif ($versioned_interpreters{$base}) {
+	my @versions = @$data[4 .. @$data - 1];
+	my @depends = map {
+	    my $d = $data->[3];
+	    $d =~ s/\$1/$_/g;
+	    $d;
+	} @versions;
+	my $depends = join (' | ', $data->[1], @depends);
+	unless (Dep::implies($deps{all}, Dep::parse($depends))) {
+	    if ($base eq 'php') {
+		tag('php-script-but-no-php-cli-dep', $filename);
+	    } elsif ($base =~ /^(wish|tclsh)/) {
+		tag("$1-script-but-no-$1-dep", $filename);
+	    } else {
+		tag("missing-dep-for-interpreter", "$base => $depends",
+		    "($filename)");
+	    }
+	}
+    } else {
+	my ($version) = ($base =~ /$data->[2]/);
+	my $depends = $data->[3];
+	$depends =~ s/\$1/$version/g;
+	unless (Dep::implies($deps{all}, Dep::parse($depends))) {
+	    if ($base =~ /^php/) {
+		tag('php-script-but-no-php-cli-dep', $filename);
+	    } elsif ($base =~ /^(python|ruby)/) {
+		tag("$1-script-but-no-$1-dep", $filename);
+	    } else {
+		tag("missing-dep-for-interpreter", "$base => $depends",
+		    "($filename)");
+	    }
+	}
     }
 }
 close(SCRIPTS);
@@ -424,24 +420,27 @@
     tag("interpreter-not-absolute", $filename, "#!$interpreter")
 	unless ($interpreter =~ m|^/|);
 
-    if (exists $valid_interpreters{$base}) {
-	tag("wrong-path-for-$base", $filename, "#!$interpreter")
-	    unless ($interpreter eq $valid_interpreters{$base});
-	tag $file eq 'config'?
-	    "forbidden-config-interpreter":"unusual-control-interpreter",
-	    "#!$interpreter"
-	    unless ($base eq 'sh'
-		    or $base eq 'bash'
-		    or $base eq 'perl');
-
-	if (exists $interpreter_dependencies{$base}) {
-	    tag("interpreter-without-predep", $filename,
-		      "#!$interpreter")
-		unless Dep::implies($deps{'pre-depends'}, Dep::parse($interpreter_dependencies{$base}));
-	} elsif ($base eq 'python') {
-	    tag("interpreter-without-predep", $filename, "#!$interpreter")
-		unless Dep::implies($deps{'pre-depends'}, Dep::parse('python | python-base'));
+    if (exists $interpreters{$base}) {
+	my $data = $interpreters{$base};
+	my $expected = $data->[0] . '/' . $base;
+	tag("wrong-path-for-interpreter", "#!$interpreter != $expected",
+	    "($filename)")
+	    unless ($interpreter eq $expected);
+	unless ($base eq 'sh' or $base eq 'bash' or $base eq 'perl') {
+	    my $tag;
+	    if ($file eq 'config') {
+		$tag = 'forbidden-config-interpreter';
+	    } else {
+		$tag = 'unusual-control-interpreter';
+	    }
+	    tag($tag, "#!$interpreter");
 	}
+	unless (defined ($data->[1]) and not $data->[1]) {
+	    my $depends = $data->[1] || $base;
+	    unless (Dep::implies($deps{'pre-depends'}, Dep::parse($depends))) {
+		tag("interpreter-without-predep", $filename, "#!$interpreter");
+	    }
+	}
     } elsif ($interpreter =~ m|/usr/local/|) {
 	tag("interpreter-in-usr-local", $filename, "#!$interpreter");
     } else {
@@ -456,12 +455,12 @@
 
     my $shellscript = $base =~ /^((b|d)?a|t?c|(pd)?k)?sh$/ ? 1 : 0;
 
+    # Only syntax-check scripts we can check with bash.
     my $checkbashisms;
     if ($shellscript) {
-        # perhaps just do it when $base eq "sh" instead?
 	$checkbashisms = $base eq "sh" ? 1 : 0;
-	if (-x $valid_interpreters{$base}) {
-	    if (check_script_syntax($interpreter, $filename)) {
+	if ($base eq 'sh' or $base eq 'bash') {
+	    if (check_script_syntax("/bin/$base", $filename)) {
 		tag("maintainer-shell-script-fails-syntax-check", $file);
 	    }
 	}

Modified: trunk/checks/scripts.desc
===================================================================
--- trunk/checks/scripts.desc	2008-01-05 05:51:39 UTC (rev 1112)
+++ trunk/checks/scripts.desc	2008-01-05 05:57:31 UTC (rev 1113)
@@ -32,7 +32,7 @@
 Tag: unusual-interpreter
 Type: warning
 Info: This package contains a script for an interpreter that the Lintian
- maintainers have not thought of.  It could be a typo for a common 
+ maintainers have not heard of.  It could be a typo for a common
  interpreter.  If not, please file a wishlist bug on lintian so that the
  Lintian maintainers can add this interpreter to their list.
 
@@ -45,53 +45,36 @@
 
 Tag: forbidden-config-interpreter
 Type: error
-Info: This package contains a 'config' script for pre-configuring the package,
- however, at that time only essential packages are guaranteed to be installed,
- so you cannot use a non-essential interpreter
+Info: This package contains a <tt>config</tt> script for pre-configuring
+ the package.  During pre-configuration, however, only essential packages
+ are guaranteed to be installed, so you cannot use a non-essential
+ interpreter.
 
 Tag: unusual-control-interpreter
 Type: info
-Info: This package contains a control script for an interpreter that
- is not normally used for control scripts.
+Info: This package contains a control script for an interpreter that is
+ not normally used for control scripts.
 
 Tag: interpreter-in-usr-local
 Type: error
-Info: This package contains a script that looks for an interpreter
- in a directory in /usr/local.  Since Debian does not install anything
- in /usr/local, this is the wrong place to look.
+Info: This package contains a script that looks for an interpreter in a
+ directory in /usr/local.  Since Debian does not install anything in
+ /usr/local, this is the wrong place to look.
 
 Tag: interpreter-without-predep
 Type: error
-Info: The package contains a control script that uses an unusual interpreter,
- but does not declare a pre-dependency on the package that provides this
- interpreter.
+Info: The package contains a control script that uses an unusual
+ interpreter, but does not declare a pre-dependency on the package that
+ provides this interpreter.
  .
- A perusal of &packaging; section 6.2 shows that any of the control scripts
- can be called while the package is not configured.  Therefore, a
+ A perusal of &packaging; section 6.2 shows that any of the control
+ scripts can be called while the package is not configured.  Therefore, a
  pre-dependency is required to ensure that the interpreter is always
  available when the script is invoked.
  .
- Please do not add a pre-dependency without following the policy for doing so.
- (Policy section 3.5).
+ Please do not add a pre-dependency without following the policy for doing
+ so. (Policy section 3.5).
 
-Tag: gawk-script-but-no-gawk-dep
-Type: error
-Info: Packages that use gawk scripts must depend on the gawk package.
- If they don't need gawk-specific features, and can just as easily work
- with mawk, then they should be awk scripts instead.
- .
- In some cases a weaker relationship, such as Suggests or Recommends, will
- be more appropriate.
-
-Tag: mawk-script-but-no-mawk-dep
-Type: error
-Info: Packages that use mawk scripts must depend on the mawk package.
- If they don't need mawk-specific features, and can just as easily work
- with gawk, then they should be awk scripts instead.
- .
- In some cases a weaker relationship, such as Suggests or Recommends, will
- be more appropriate.
-
 Tag: missing-dep-for-interpreter
 Type: error
 Info: You used an interpreter for a script that is not in an essential
@@ -115,99 +98,91 @@
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
-Tag: php-script-but-no-php-cli-dep
+Tag: wrong-path-for-interpreter
 Type: error
-Info: Packages that use PHP scripts with /usr/bin/php as interpreter must
- depend on a php-cli package (such as php4-cli or php5-cli). Note that a
- dependency on a php-cgi package (such as php5-cgi) is needlessly strict,
- and forces the user to install a package that isn't needed.
+Info: The interpreter you used is installed at another location on Debian
+ systems.
+
+Tag: gawk-script-but-no-gawk-dep
+Type: error
+Info: Packages that use gawk scripts must depend on the gawk package.
+ If they don't need gawk-specific features, and can just as easily work
+ with mawk, then they should be awk scripts instead.
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
-Tag: php4-script-but-no-php4-cli-dep
+Tag: mawk-script-but-no-mawk-dep
 Type: error
-Info: Packages that use PHP4 scripts must depend on the php4-cli package. Note
- that a dependency on php4-cgi is needlessly strict, and forces the user to
- install a package that isn't needed.
+Info: Packages that use mawk scripts must depend on the mawk package.
+ If they don't need mawk-specific features, and can just as easily work
+ with gawk, then they should be awk scripts instead.
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
-Tag: php5-script-but-no-php5-cli-dep
+Tag: php-script-but-no-php-cli-dep
 Type: error
-Info: Packages that use PHP5 scripts must depend on the php5-cli package. Note
- that a dependency on php5-cgi is needlessly strict, and forces the user to
- install a package that isn't needed.
+Info: Packages with PHP scripts must depend on a php-cli package such as
+ php5-cli.  Note that a dependency on a php-cgi package (such as php5-cgi)
+ is needlessly strict and forces the user to install a package that isn't
+ needed.
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
-Tag: wrong-path-for-python
-Type: error
-Info: Python is installed as /usr/bin/python on Debian systems.
- .
- Specific Python versions are installed as /usr/bin/pythonX.Y
-
-Tag: wrong-path-for-ruby
-Type: error
-Info: Ruby is installed as /usr/bin/ruby on Debian systems.
- .
- Specific Ruby versions are installed as /usr/bin/rubyX.Y
-
-Tag: wrong-path-for-interpreter
-Type: error
-Info: The interpreter you used is installed at another location on Debian systems.
-
 Tag: python-script-but-no-python-dep
 Type: error
-Info: Packages with scripts that are executed with python must depend on the
- package python. Those that have scripts executed with a versioned python
- package need a dependency on the equivalent version of python.
+Info: Packages with Python scripts must depend on the package python.
+ Those that have scripts executed with a versioned python package need a
+ dependency on the equivalent version of python. 
  .
- For example, if a script in the package uses #!/usr/bin/python, then the
- package needs a dependency on "python". If a script uses
- #!/usr/bin/python2.2, then the package need a dependency on "python2.2".
+ For example, if a script in the package uses <tt>#!/usr/bin/python</tt>,
+ the package needs a dependency on "python".  If a script uses
+ <tt>#!/usr/bin/python2.5</tt>, the package need a dependency on
+ "python2.5".
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
 Tag: ruby-script-but-no-ruby-dep
 Type: error
-Info: Packages with scripts that are executed with ruby must depend on the
- package ruby. Those that have scripts executed with a versioned ruby
- package need a dependency on the equivalent version of ruby.
+Info: Packages with Ruby scripts must depend on the package ruby. Those
+ that have Ruby scripts that run under a specific version of Ruby need a
+ dependency on the equivalent version of Ruby.
  .
- For example, if a script in the package uses #!/usr/bin/ruby, then the
- package needs a dependency on "ruby". If a script uses
- #!/usr/bin/ruby1.6, then the package need a dependency on "ruby1.6".
+ For example, if a script in the package uses <tt>#!/usr/bin/ruby</tt>,
+ the package needs a dependency on "ruby".  If a script uses
+ <tt>#!/usr/bin/ruby1.9</tt>, then the package need a dependency on
+ "ruby1.9".
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
 Tag: wish-script-but-no-wish-dep
 Type: error
-Info: Packages that use wish scripts must depend on the virtual package wish
- or, if they require a specific version of wish or tk, that version of tk.
+Info: Packages that include wish scripts must depend on the virtual
+ package wish or, if they require a specific version of wish or tk, that
+ version of tk.
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
 Tag: tclsh-script-but-no-tclsh-dep
 Type: error
-Info: Packages that use wish scripts must depend on the virtual package
- tclsh or, if they require a specific version of wish or tk, that version
- of tcl.
+Info: Packages that include tclsh scripts must depend on the virtual
+ package tclsh or, if they require a specific version of tcl, that
+ version of tcl.
  .
  In some cases a weaker relationship, such as Suggests or Recommends, will
  be more appropriate.
 
 Tag: calls-suidperl-directly
 Type: error
-Info: Since perl version 5.8.3-3, /usr/bin/suidperl shouldn't be called directly
- anymore (and doing so will lead to errors in most cases) but the script should
- just use /usr/bin/perl as interpreter which will call suidperl automatically if
- the script has the suid permission bit set.
+Info: Since perl version 5.8.3-3, /usr/bin/suidperl shouldn't be called
+ directly anymore (and doing so will lead to errors in most cases) but the
+ script should just use /usr/bin/perl as interpreter which will call
+ suidperl automatically if the script has the suid permission bit set.
 
 Tag: shell-script-fails-syntax-check
 Type: error
@@ -226,20 +201,19 @@
 
 Tag: possibly-insecure-handling-of-tmp-files-in-maintainer-script
 Type: warning
-Info: The maintainer script seems to access a file in <tt>/tmp</tt> or some
- other temporary directory. Since creating temporary files in a
+Info: The maintainer script seems to access a file in <tt>/tmp</tt> or
+ some other temporary directory. Since creating temporary files in a
  world-writable directory is very dangerous, this is likely to be a
- security bug. It's suggested that you use the <tt>tempfile</tt> or
- <tt>mktemp</tt> utilities to create temporary files in these
- directories.
+ security bug. Use the <tt>tempfile</tt> or <tt>mktemp</tt> utilities to
+ create temporary files in these directories.
 Ref: policy 10.4
 
 Tag: killall-is-dangerous
 Type: warning
 Info: The maintainer script seems to call <tt>killall</tt>.  Since this
  utility kills processes by name, it may well end up killing unrelated
- processes.  Most uses of <tt>killall</tt> should use
- <tt>start-stop-daemon</tt> instead.
+ processes.  Most uses of <tt>killall</tt> should use <tt>invoke-rc.d</tt>
+ instead.
 
 Tag: mknod-in-maintainer-script
 Type: error
@@ -279,9 +253,8 @@
 
 Tag: suidregister-used-in-maintainer-script
 Type: error
-Info: This script calls suidregister which is no longer needed, a new
- command 'dpkg-statoverride' gives admins more flexibility.  Please see
- the documentation of suidmanager and dpkg-statoverride for details.
+Info: This script calls suidregister, a long-obsolete program that has
+ been replaced by dpkg-statoverride.
 
 Tag: maintainer-script-needs-depends-on-update-inetd
 Type: warning
@@ -320,24 +293,25 @@
 
 Tag: update-alternatives-remove-called-in-postrm
 Type: warning
-Info: 'update-alternatives --remove &lt;alternative&gt; foo' is called in the
- postrm.  This can be dangerous because at the time the postrm is executed
- foo has already been deleted and update-alternatives will ignore it while
- constructing its list of available alternatives.  Then, if the
- /etc/alternatives symlink points at foo, update-alternatives won't
- recognize it and will mark the symlink as something site-specific.  As
- such, the symlink will no longer be updated automatically and will be
- left dangling until `update-alternatives --auto &lt;alternative&gt;' is
- run by hand.
+Info: <tt>update-alternatives --remove &lt;alternative&gt; foo</tt> is
+ called in the postrm.  This can be dangerous because at the time the
+ postrm is executed foo has already been deleted and update-alternatives
+ will ignore it while constructing its list of available alternatives.
+ Then, if the /etc/alternatives symlink points at foo, update-alternatives
+ won't recognize it and will mark the symlink as something site-specific.
+ As such, the symlink will no longer be updated automatically and will be
+ left dangling until <tt>update-alternatives --auto
+ &lt;alternative&gt;</tt> is run by hand.
  .
- update-alternatives --remove should be called in the prerm instead.
+ <tt>update-alternatives --remove</tt> should be called in the prerm
+ instead.
 
 Tag: deprecated-chown-usage
 Type: warning
-Info: 'chown user.group' is called in one of the maintainer scripts.
- This should be avoided, as the correct syntax is 'chown user:group'.
- Using "." as a separator is still supported by the GNU tools, but it will
- fail as soon as a system uses the "." in user or group names.
+Info: <tt>chown user.group</tt> is called in one of the maintainer
+ scripts.  The correct syntax is <tt>chown user:group</tt>. Using "." as a
+ separator is still supported by the GNU tools, but it will fail as soon
+ as a system uses the "." in user or group names.
 
 Tag: maintainer-script-hides-init-failure
 Type: warning

Modified: trunk/debian/changelog
===================================================================
--- trunk/debian/changelog	2008-01-05 05:51:39 UTC (rev 1112)
+++ trunk/debian/changelog	2008-01-05 05:57:31 UTC (rev 1113)
@@ -65,10 +65,17 @@
   * checks/patch-systems:
     + [RA] dpatch permits multiple patches to be listed on the same line
       of 00list.  Patch by Chris Lamb.  (Closes: #457523)
-  * checks/scripts:
+  * checks/scripts{.desc,}:
     + [RA] Add lua40 and lua5.1.  Thanks, Enrico Tassi.  (Closes: #457219)
     + [RA] Improve recognition of heredocs.
     + [RA] Recognize quoted strings that start at beginning of the line.
+    + [RA] Rewrite script path and dependency checking.  Remove scripts
+      and packages no longer in the archive.  Add new versions of
+      versioned scripts and packages.  Fix the dependencies for pike
+      interpreters.  (Closes: #458896)
+    + [RA] Reformat long descriptions and collapse some tags.
+    + [RA] For consistent results, only syntax-check sh and bash scripts.
+      Also ignore all dpatch files, not just those in /usr/src.
   * checks/shared-libs{.desc,}:
     + [RA] New check for version numbers in symbol files.  Based on a
       patch from Raphael Hertzog.  (Closes: #457067)

Modified: trunk/testset/scripts/debian/rules
===================================================================
--- trunk/testset/scripts/debian/rules	2008-01-05 05:51:39 UTC (rev 1112)
+++ trunk/testset/scripts/debian/rules	2008-01-05 05:57:31 UTC (rev 1113)
@@ -23,6 +23,7 @@
 	install -m 755 csh-foo $(tmp)/etc/csh/login.d/ 
 	install -m 755 envfoo $(tmp)/usr/bin/
 	install -m 755 fish-foo $(tmp)/etc/fish.d/
+	install -m 755 jruby-broken $(tmp)/usr/bin/
 	install -m 755 pyfoo $(tmp)/usr/bin/
 	install -m 755 py2foo $(tmp)/usr/bin/
 	install -m 755 perlfoo $(tmp)/usr/bin/
@@ -30,6 +31,7 @@
 	install -m 755 make-foo $(tmp)/usr/bin/
 	install -m 755 lefty-foo $(tmp)/usr/bin/
 	install -m 4751 perlfoo $(tmp)/usr/bin/suidperlfoo2
+	install -m 755 sh-broken $(tmp)/usr/bin/
 	install -m 4555 suidperlfoo $(tmp)/usr/bin/
 	install -m 755 tkfoo $(tmp)/usr/bin/
 	install -m 755 wishfoo $(tmp)/usr/bin/

Added: trunk/testset/scripts/jruby-broken
===================================================================
--- trunk/testset/scripts/jruby-broken	                        (rev 0)
+++ trunk/testset/scripts/jruby-broken	2008-01-05 05:57:31 UTC (rev 1113)
@@ -0,0 +1,2 @@
+#!/usr/bin/jruby
+# There's no non-versioned jruby, so this should be an error.

Added: trunk/testset/scripts/sh-broken
===================================================================
--- trunk/testset/scripts/sh-broken	                        (rev 0)
+++ trunk/testset/scripts/sh-broken	2008-01-05 05:57:31 UTC (rev 1113)
@@ -0,0 +1,2 @@
+#!/bin/sh
+if fi

Modified: trunk/testset/tags.scripts
===================================================================
--- trunk/testset/tags.scripts	2008-01-05 05:51:39 UTC (rev 1112)
+++ trunk/testset/tags.scripts	2008-01-05 05:57:31 UTC (rev 1113)
@@ -8,14 +8,14 @@
 E: scripts: init.d-script-has-duplicate-lsb-section /etc/init.d/lsb-broken
 E: scripts: init.d-script-has-unterminated-lsb-section /etc/init.d/lsb-broken:15
 E: scripts: missing-dep-for-interpreter lefty => graphviz (./usr/bin/lefty-foo)
+E: scripts: php-script-but-no-php-cli-dep ./usr/share/scripts/php5foo
 E: scripts: php-script-but-no-php-cli-dep ./usr/share/scripts/phpfoo
-E: scripts: php5-script-but-no-php5-cli-dep ./usr/share/scripts/php5foo
 E: scripts: python-script-but-no-python-dep ./usr/bin/py2foo
 E: scripts: python-script-but-no-python-dep ./usr/bin/pyfoo
-E: scripts: shell-script-fails-syntax-check ./usr/share/scripts/gccbug.dpatch
+E: scripts: shell-script-fails-syntax-check ./usr/bin/sh-broken
 E: scripts: suid-perl-script-but-no-perl-suid-dep ./usr/bin/suidperlfoo2
+E: scripts: wrong-path-for-interpreter #!/bin/ruby1.8 != /usr/bin/ruby1.8 (./usr/bin/rubyfoo)
 E: scripts: wrong-path-for-interpreter #!/usr/local/bin/lefty != /usr/bin/lefty (./usr/bin/lefty-foo)
-E: scripts: wrong-path-for-ruby ./usr/bin/rubyfoo #!/bin/ruby1.8
 I: scripts: no-md5sums-control-file
 W: scripts source: ancient-standards-version 3.2.1 (current is 3.7.3)
 W: scripts source: binary-arch-rules-but-pkg-is-arch-indep
@@ -27,6 +27,7 @@
 W: scripts source: source-nmu-has-incorrect-version-number 6
 W: scripts source: uses-dh-python-with-no-pycompat
 W: scripts: binary-without-manpage usr/bin/envfoo
+W: scripts: binary-without-manpage usr/bin/jruby-broken
 W: scripts: binary-without-manpage usr/bin/lefty-foo
 W: scripts: binary-without-manpage usr/bin/make-foo
 W: scripts: binary-without-manpage usr/bin/perl-bizarre-1
@@ -36,6 +37,7 @@
 W: scripts: binary-without-manpage usr/bin/py2foo
 W: scripts: binary-without-manpage usr/bin/pyfoo
 W: scripts: binary-without-manpage usr/bin/rubyfoo
+W: scripts: binary-without-manpage usr/bin/sh-broken
 W: scripts: binary-without-manpage usr/bin/suidperlfoo
 W: scripts: binary-without-manpage usr/bin/suidperlfoo2
 W: scripts: binary-without-manpage usr/bin/test.sh
@@ -61,3 +63,4 @@
 W: scripts: script-with-language-extension usr/bin/test.sh
 W: scripts: setuid-binary usr/bin/suidperlfoo 4555 root/root
 W: scripts: setuid-binary usr/bin/suidperlfoo2 4751 root/root
+W: scripts: unusual-interpreter ./usr/bin/jruby-broken #!/usr/bin/jruby


Reply to: