Bug#969458: perl crash in eval command trying a failing require statement
Niko Tyni
ntyni at debian.org
Thu Sep 3 20:30:22 BST 2020
On Thu, Sep 03, 2020 at 12:13:06PM +0200, Raphaƫl Hertzog wrote:
> Package: perl
> Version: 5.30.3-4
> Severity: important
> User: devel at kali.org
> Usertags: origin-kali
> X-Debbugs-Cc: debian-dpkg at lists.debian.org
> Control: found -1 5.32.0-2
>
> In Kali, any source package build started to fail with a mysterious
> error:
> > dpkg-buildpackage: error: dpkg-source -b . subprocess returned exit status 127
>
> After quite some investigation, I tracked this down to perl exiting with
> that error code in the middle of an eval statement that should have failed:
> https://sources.debian.org/src/dpkg/1.20.5/scripts/Dpkg/Vendor.pm/#L166
>
> The $name tried is "Kali" and we don't ship any Dpkg::Vendor::Kali. The
> code should fallback to Dpkg::Vendor::Debian and this works a few times
> but after multiples calls, at some point it no longer works and the
> require statement in the eval block just never returns, it seems to crash
> the perl interpreter.
This looks like a bug in dpkg to me.
I got it down to this:
------------------------------------------------
#!/usr/bin/perl
use strict;
use warnings;
use Dpkg::Exit;
use Dpkg::Vendor;
Dpkg::Exit::push_exit_handler(sub { }) ;
Dpkg::Vendor::get_vendor_object();
------------------------------------------------
Getting Dpkg::Vendor out of it:
------------------------------------------------
#!/usr/bin/perl
use strict;
use warnings;
use Dpkg::Exit qw(push_exit_handler);
Dpkg::Exit::push_exit_handler(sub { }) ;
eval { require NonExistent };
warn "survived: $@";
------------------------------------------------
(which doesn't survive), and simplifying further:
------------------------------------------------
#!/usr/bin/perl
use strict;
use warnings;
$SIG{__DIE__} = sub { exit 127 };
eval { require NonExistent };
warn "survived: $@";
------------------------------------------------
So dpkg is installing a __DIE__ handler that exits with 127,
which then gets triggered when require() fails.
I suspect the Perl side is working as designed?
--
Niko Tyni ntyni at debian.org
More information about the Perl-maintainers
mailing list