Permalink
Browse files

Manage Devel::Cover coverage reporting errors.

Devel::Cover errors in _report() would end the process.  That wouldn't
normally matter since Devel::Cover tries very hard to be the last thing to be
run anyway.

But it is important just before an exec().  When Devel::Cover sees an exec()
call it first calls report() then calls the exec().  In this case it is
important that any errors in report() do not prevent the exec() from running.

We go belt and braces here: put an eval {} around the _report() and try to
nicely report the problem, and add G_EVAL to call_pv().

Also add a test for this.

This problem was found by Daisuke Maki.  He also diagnosed it, provided the
test case and suggested the solution.
  • Loading branch information...
1 parent d2de994 commit 1716d034743015f30de4ddc25d6525f5cc0d7955 @pjcj committed Oct 14, 2011
Showing with 98 additions and 2 deletions.
  1. +1 −1 Cover.xs
  2. +18 −1 lib/Devel/Cover.pm
  3. +59 −0 test_output/cover/exec_die.5.006001
  4. +20 −0 tests/exec_die
View
@@ -412,7 +412,7 @@ static void call_report(pTHX)
{
dSP;
PUSHMARK(SP);
- call_pv("Devel::Cover::report", G_VOID|G_DISCARD);
+ call_pv("Devel::Cover::report", G_VOID|G_DISCARD|G_EVAL);
SPAGAIN;
}
View
@@ -661,7 +661,24 @@ my %Seen;
sub report
{
- _report();
+ local $@;
+ eval
+ {
+ _report();
+ };
+ if ($@)
+ {
+ print STDERR <<"EOM" unless $Silent;
+Devel::Cover: Oops, it looks like something went wrong writing the coverage.
+ It's possible that more bad things may happen but we'll try to
+ carry on anyway as if nothing happened. At a minimum you'll
+ probably find that you are missing coverage. If you're
+ interrested, the problem was:
+
+$@
+
+EOM
+ }
return unless $Self_cover;
$Self_cover_run = 1;
_report();
@@ -0,0 +1,59 @@
+Reading database from ...
+
+
+------------------------------------------ ------ ------ ------ ------ ------
+File stmt bran cond sub total
+------------------------------------------ ------ ------ ------ ------ ------
+tests/exec_die 50.0 50.0 n/a 0.0 44.4
+Total 50.0 50.0 n/a 0.0 44.4
+------------------------------------------ ------ ------ ------ ------ ------
+
+
+Run: ...
+Perl version: ...
+OS: ...
+Start: ...
+Finish: ...
+
+tests/exec_die
+
+line err stmt bran cond sub code
+1 #!/usr/bin/perl
+2
+3 # Copyright 2007-2011, Paul Johnson (pjcj@cpan.org)
+4
+5 # This software is free. It is licensed under the same terms as Perl itself.
+6
+7 # The latest version of this software should be available from my homepage:
+8 # http://www.pjcj.net
+9
+10 1 my $pid = fork;
+11
+12 *** 1 50 if ($pid)
+13 {
+14 1 wait;
+15 }
+16 else
+17 {
+18 *** 0 0 local *Devel::Cover::_report = sub { die "Badness happened!" };
+ *** 0
+19 *** 0 exec "echo We want to be able to see this.";
+20 }
+
+
+Branches
+--------
+
+line err % true false branch
+----- --- ------ ------ ------ ------
+12 *** 50 1 0 if ($pid) { }
+
+
+Uncovered Subroutines
+---------------------
+
+Subroutine Count Location
+---------- ----- -----------------
+__ANON__ 0 tests/exec_die:18
+
+
View
@@ -0,0 +1,20 @@
+#!/usr/bin/perl
+
+# Copyright 2007-2011, Paul Johnson (pjcj@cpan.org)
+
+# This software is free. It is licensed under the same terms as Perl itself.
+
+# The latest version of this software should be available from my homepage:
+# http://www.pjcj.net
+
+my $pid = fork;
+
+if ($pid)
+{
+ wait;
+}
+else
+{
+ local *Devel::Cover::_report = sub { die "Badness happened!" };
+ exec "echo We want to be able to see this.";
+}

2 comments on commit 1716d03

Contributor

wchristian replied Oct 15, 2011

This might need to be skipped on Windows, due to fork being uselessly implemented there.

I'm getting this:

t/e2e/aexec_die.t ........... Cannot close C:\Perl\bin\perl.exe -ID:/Devel--Cover/Devel-Cover-0.79/ -ID:/Devel--Cover/Devel-Cover-0.79/blib/lib -ID:/Devel--Cover/Devel-Cover-0.79/blib/arch -MDevel::Cover=-db,D:/Devel--Cover/Devel-Cover-0.79/t/e2e/cover_db_exec_die/,-select,exec_die,-ignore,blib,Devel/Cover,-merge,0,-coverage,statement,branch,condition,subroutine D:/Devel--Cover/Devel-Cover-0.79/tests/exec_die :  at D:/Devel--Cover/Devel-Cover-0.79/blib/lib/Devel/Cover/Test.pm line 203.
END failed--call queue aborted.
t/e2e/aexec_die.t ........... Dubious, test returned 3 (wstat 768, 0x300)
Failed 1/1 subtests

And:

d:\Devel--Cover\Devel-Cover-0.79>C:\Perl\bin\perl.exe -ID:/Devel--Cover/Devel-Cover-0.79/ -ID:/Devel--Cover/Devel-Cover-0.79/blib/lib -ID:/Devel--Cover/Devel-Cover-0.79/blib/arch -MDevel::Cover=-db,D:/Devel--Cover/Devel-Cover-0.79/t/e2e/cover_db_exec_die/,-select,exec_die,-ignore,blib,Devel/Cover,-merge,0,-coverage,statement,branch,condition,subroutine D:/Devel--Cover/Devel-Cover-0.79/tests/exec_die
Devel::Cover 0.001: Collecting coverage data for branch, condition, statement and subroutine.
Selecting packages matching:
    exec_die
Ignoring packages matching:
    blib
    Devel/Cover
    ^t/
    \.t$
    ^test\.pl$
Ignoring packages in:
    .
    C:/Perl/lib
    C:/Perl/site/lib

Unfortunately, Devel::Cover does not yet work with threads.  I have done
some work in this area, but there is still more to be done.


This application has requested the Runtime to terminate it in an unusual way.
Please contact the application's support team for more information.

d:\Devel--Cover\Devel-Cover-0.79>
Owner

pjcj replied Oct 15, 2011

Quite right. Fixed (hopefully) by c6f1710, but not tested.

Thanks.

Please sign in to comment.