You are viewing a plain text version of this content. The canonical link for it is here.
Posted to modules-dev@httpd.apache.org by Jacob Champion <ja...@ni.com> on 2015/06/02 21:15:18 UTC

Signal-safe way to start a worker thread in each child process?

Hello all,

We're developing an Apache module that requires a background thread to
be running in each individual child process. We've been calling
apr_thread_create() during the child_init hook, and at first that
appeared to work. Then we started seeing intermittent hangs on worker
shutdown.

We found out that our background thread was intercepting signals that
were meant for the main thread. Apparently the apr_setup_signal_thread()
function is meant to prevent this from happening; its documentation
says, "Warning: This must be called before any threads are created."
Unfortunately, mpm_worker calls apr_setup_signal_thread() _after_ it
runs the child_init hooks (see the child_main() implementation in
server/mpm/worker/worker.c), so we're not getting its protection.

We could just call apr_setup_signal_thread() ourselves -- and doing that
does fix the problem -- but that means that modules which are
initialized after us will get the global protection too, which doesn't
feel clean. So, a few questions:

1) Is creating a new thread during the child_init hook the correct way
to ensure that each child process gets its own background thread?

2) If so, is it intended behavior that Apache calls
apr_setup_signal_thread() after the child_init hook, instead of before it?

In case it matters, this is httpd 2.4.10 on Linux. Thanks for your time!

Jacob Champion
LabVIEW R&D
National Instruments

Re: Signal-safe way to start a worker thread in each child process?

Posted by Jacob Champion <ja...@ni.com>.
On 6/3/2015 1:02 PM, Yann Ylavic wrote:
> On Wed, Jun 3, 2015 at 7:55 PM, Jacob Champion <ja...@ni.com> wrote:
>>
>> In your opinion, is this worth filing a bug report over?
> 
> That would probably help to remember that there is a request for it ;)

Done: https://bz.apache.org/bugzilla/show_bug.cgi?id=57997

Thanks again, everyone.

Jacob Champion
LabVIEW R&D
National Instruments

Re: Signal-safe way to start a worker thread in each child process?

Posted by Yann Ylavic <yl...@gmail.com>.
On Wed, Jun 3, 2015 at 7:55 PM, Jacob Champion <ja...@ni.com> wrote:
>
> In your opinion, is this worth filing a bug report over?

That would probably help to remember that there is a request for it ;)

Regards,
Yann.

Re: Signal-safe way to start a worker thread in each child process?

Posted by Jacob Champion <ja...@ni.com>.
Yann,

On 6/2/2015 3:19 PM, Yann Ylavic wrote:
> A workaround today is (as you did) to use the child_init hook
> registered with APR_HOOK_REALLY_LAST, so that it is called after all
> the others.

Great, that should help mitigate the risk for now; thank you! (Thanks to
Nick as well for his similar suggestion.)

In your opinion, is this worth filing a bug report over?

Jacob Champion
LabVIEW R&D
National Instruments

Re: Signal-safe way to start a worker thread in each child process?

Posted by Yann Ylavic <yl...@gmail.com>.
Hello,

On Tue, Jun 2, 2015 at 9:15 PM, Jacob Champion <ja...@ni.com> wrote:
>
> We could just call apr_setup_signal_thread() ourselves -- and doing that
> does fix the problem -- but that means that modules which are
> initialized after us will get the global protection too, which doesn't
> feel clean. So, a few questions:
>
> 1) Is creating a new thread during the child_init hook the correct way
> to ensure that each child process gets its own background thread?

I would say yes, currently, with the existing hooks (run by the
children processes)...

>
> 2) If so, is it intended behavior that Apache calls
> apr_setup_signal_thread() after the child_init hook, instead of before it?

I don't know if it's intended, but that's the current behaviour.
Maybe a new hook is needed after apr_setup_signal_thread(), that would
not be a huge change (backportable/acceptable IMHO).

A workaround today is (as you did) to use the child_init hook
registered with APR_HOOK_REALLY_LAST, so that it is called after all
the others.
Since the hook will also be called just before
apr_setup_signal_thread(), and the latter can be called multiple
times, it should work without causing any issue.

Regards,
Yann.

Re: Signal-safe way to start a worker thread in each child process?

Posted by Nick Kew <ni...@apache.org>.
On Tue, 02 Jun 2015 14:15:18 -0500
Jacob Champion <ja...@ni.com> wrote:

> We could just call apr_setup_signal_thread() ourselves -- and doing that
> does fix the problem -- but that means that modules which are
> initialized after us will get the global protection too, which doesn't
> feel clean. So, a few questions:

I don't know a clean answer: it's not a problem I've ever tackled.
But if you don't find a better solution, you can improve a little
on your existing one by running your child_init after other modules
have done theirs with APR_HOOK_LAST.

-- 
Nick Kew