-------------8<---------- Start Bug Report ------------8<---------- 1. Problem Description:
I'm trying to make a PerlFixupHandler that reads:
sub ssl_is_mandatory { my $r = shift; require Apache::RequestRec; return 403 unless defined($r->subprocess_env("SSL_SERVER_S_DN")); return 0 } Apache->push_handlers("PerlFixupHandler", \&ssl_is_mandatory);
So far so good, but when I try to do this instead:
Apache->push_handlers("PerlFixupHandler", sub { ... });
where do you call the above, Dominique? At the server startup?
with the exact same Perl code inside the sub as above, I get extremely weird error messages, namely a warning ("Use of uninitialized value in null operation") and an error ("Undefined subroutine &main:: called"), neither of which having any useful backtrace information according to Apache::DB and some crocky breakpoints in $SIG{__WARN__} and $SIG{__DIE__} that I put together: for example,[...]
DB<1> T
$ = IDX::Debug::_die_with_stack_trace('Undefined subroutine &main:: called.^J') called from -e line 0
$ = eval {...} called from -e line 0
So this looks a lot like modperl_callback is calling a CV that has been free()d before at modperl_callback line 100. Being a nearly complete ignorant in XS, I cannot investigate much further on my own, but I can certainly run experiments on your behalf, apply patches, etc.
This problem isn't blocking me anymore as I found an adequate workaround, namely to not use an anonymous sub (albeit after 2 days of debugging). So please, Stas and all, don't rush to rescue me, it's very nice of you but a bit embarassing at times :-)
Here is some explanation of what's happening inside:
/* How anon-subs are handled: * We have two ways anon-subs can be registered * A) at startup from httpd.conf: * PerlTransHandler 'sub { ... }' * B) run-time perl code * $r->push_handlers(PerlTransHandler => sub { .... }); * * In the case of non-threaded perl, we just compile A or grab B and * store it in the mod_perl struct and call it when it's used. No * problems here * * In the case of threads, things get more complicated. we no longer * can store the CV value of the compiled anon-sub, since when * perl_clone is called each interpreter will have a different CV * value. since we need to be able to have 1 entry for each anon-sub * across all interpreters a different solution is needed. to remind * in the case of named subs, we just store the name of the sub and * look its corresponding CV when we need it. * * The used solution: each process has a global counter, which always * grows. Every time a new anon-sub is encountered, a new ID is * allocated from that process-global counter and that ID is stored in * the mod_perl struct. The compiled CV is stored as * $PL_modglobal{ANONSUB}{$id} = CV; * when perl_clone is called, each clone will clone that CV value, but * we will still be able to find it, since we stored it in the * hash. so we retrieve the CV value, whatever it is and we run it. * * that explanation can be written and run in perl: * * use threads; * our %h; * $h{x} = eval 'sub { print qq[this is sub @_\n] }'; * $h{x}->("main"); * threads->new(sub { $h{x}->(threads->self->tid)}); * * XXX: more nuances will follow */
but I'm confused as you are using 5.6.1 w/o threads. it should have worked there just fine.
Any chance you could add a test to the modperl2 test suite that I can reproduce the problem with? If you don't manage to I'll try to write one. You can take a look at one of:
t/hooks/TestHooks/inlined_handlers.pm t/hooks/TestHooks/push_handlers_same_phase.pm t/hooks/TestHooks/stacked_handlers2.pm t/hooks/TestHooks/stacked_handlers.pm t/hooks/TestHooks/push_handlers_blessed.pm t/hooks/TestHooks/set_handlers.pm t/hooks/TestHooks/push_handlers.pm
Thanks.
-- __________________________________________________________________ Stas Bekman JAm_pH ------> Just Another mod_perl Hacker http://stason.org/ mod_perl Guide ---> http://perl.apache.org mailto:[EMAIL PROTECTED] http://use.perl.org http://apacheweek.com http://modperlbook.org http://apache.org http://ticketmaster.com