Last week I had a problem where I could not get my Apache2/mod_perl2/perl5.8.3 web server to catch a SIGPIPE signal in a timely manner. I was asked to post a description of this problem and solution to this list so that it might be included in future mod_perl documentation.

Feel free to adjust this description as necessary when integrating it into the appropriate documentation.

The Problem:
Use a PerlFixupHandler to catch when the pipe from browser to httpd server has been broken such as when the user presses the browser stop button.


In conf.d/perl.conf
PerlFixupHandler Apache::SIG2

where Apache::SIG2.pm is defined in this example as:

----------
package Apache::SIG2;

# This package adapted by Jim Albert from the original mod_perl1
# Apache::SIG.pm by Doug MacEachern and Doug Bagley
# This PerlHandler can be used to prevent httpd children from killing
# off non-mod-perled CGIs when the user presses the Stop button.

use strict;
use Apache::RequestRec;
use ModPerl::Util;
use Apache::Const;

sub handler {
    my $r = shift;
    if (!$r->main) {
        $SIG{PIPE} = \&PIPE;
    }

   return OK;
}

sub PIPE {
   my($signal) = @_;
   print STDERR ("User pressed stop button.\n");
   # Kill off the httpd child before it can kill any running CGIs.
   # Or do whatever other cleanup is appropriate.
   CORE::exit();
}

1;
----------

With the introduction of perl 5.8.0, this handler no longer works as expected because of the introduction of perl safe signals.
See:
http://www.perldoc.com/perl5.8.4/pod/perlipc.html#Deferred-Signals-(Safe-Signals)


What happens with perl 5.8 and safe signals is that the apache httpd child does receive the SIGPIPE, but it is delayed and the perl CGI program has already been killed. The httpd child does not act on the SIGPIPE until it receives the next httpd request.

The Solution:
An Apache server_startup.pl script can be used to turn off perl safe signals with the following line:
$ENV{PERL_SIGNALS} = "unsafe";
The server_startup.pl script can be included via the following line in perl.conf:
PerlRequire conf/server_startup.pl
The ability to revert back to "unsafe" signals is available as of perl 5.8.1.


--
Jim Albert



--
Report problems: http://perl.apache.org/bugs/
Mail list info: http://perl.apache.org/maillist/modperl.html
List etiquette: http://perl.apache.org/maillist/email-etiquette.html



Reply via email to