The underlying cause appears to be that libm is referencing
_LIB_VERSION in libperl.

I suspect the Oracle client libraries have dlopen()ed a library that
depends on libm, and that isn't dlclosed() when mod_perl unloads
DBD::Oracle.

So the process that leads to the crash:

1) Apache starts it configuration check[1], loads mod_perl, which
implicitly loads libperl (with PL_keyword_plugin set to its default)

2) mod_perl runs the startup script, loading Syntax::Keyword::Try
(which points PL_keyword_plugin at its keyword handler) and
DBD::Oracle (which presumably dlopen()s a shared object that depends
on libm).

3) Apache unloads mod_perl, which unloads the shared objects for
Syntax::Keyword::Try and DBD::Oracle.

Since something still loaded depends on libm, and that depends on the
_LIB_VERSION symbol defined by libperl, libperl remains loaded.

PL_keyword_plugin now points to where the Syntax::Keyword::Try keyword
handler *used* to be.

4) Apache loads mod_perl again, and attempts to parse the perl startup
script.  Since PL_keyword_plugin points to unmapped memory, libperl
segfaults.

Without something else depending on libm, libperl would normally be
unloaded at step 3), and step 4) would reload libperl, with
PL_keyword_plugin pointing at the default keyword plugin function.

The patch incidentally prevents libm depending on the _LIB_VERSION
symbol in libperl, so libperl can unload when mod_perl unloads.

Tony

[1] https://wiki.apache.org/httpd/ModuleLife

Reply via email to