[Mono-dev] Handling StackOverflow, OutOfMemory, ThreadAbortException
kumpera at gmail.com
Wed Feb 1 21:22:33 UTC 2012
On Wed, Feb 1, 2012 at 1:39 PM, Miguel Mudge
<michael.mudge at welchallyn.com>wrote:
> On Wed, Feb 1, 2012 at 9:48 AM, Rodrigo Kumpera <kumpera at gmail.com> wrote:
>> On Wed, Feb 1, 2012 at 12:22 PM, Miguel Mudge <
>> michael.mudge at welchallyn.com> wrote:
>>> Yes, it's got machine exceptions. With the help of the MMU, we are able
>>> to detect when the stack is down to the last 64K, so there is no need for
>>> an alternate stack. We can call a function from there, somewhat akin to
>> On which stack and thread is that function called? You obviously can't
>> call it on the overflown one.
> The RTOS is ThreadX for ARM - it is fairly useless. Mono is supported
> mostly by a homebrew POSIX implementation wrapped around it [cringe].
> We wrote our own MMU driver. When an overflow occurs, we increase the
> size of the stack on the fly and call the overflow-handling function on the
> same thread and stack where the overflow occurred. When that function
> returns, execution resumes on the instruction that caused the overflow, but
> this time with the larger stack.
>> The requirements are that:
>>> - The native code is allowed to continue execution.
>>> - The managed code throws a StackOverflowException that executes finally
>>> - The root AppDomain continues running.
>>> The out-of-memory exception is almost the exact same story... When
>>> memory gets low, I want to be able to do something that allows native code
>>> to continue, but OutOfMemoryException is thrown when execution returns to
>>> managed code. I assume there is no mechanism in there for this?
>> OOM is quite a different beast, it's handled synchronously since we know
>> exactly when we're out of managed memory. Mono doesn't handle native
>> allocation failures
>> well and this is something I would love to see patches for. Managed
>> allocation failures are well handled with sgen.
> Since Mono doesn't handle running out of system memory very well, I'd
> rather actually handle it in exactly the same way as StackOverflowException
> - free up some "guard memory" and throw the OutOfMemoryException when
> execution returns to native code.
> In the context of our own requirements, I still see ThreadAbortException,
> StackOverflowException and OutOfMemoryException as ideally following the
> same code path. In all 3 cases, a specific thread isn't prepared to handle
> the exception on the the exact instruction where it happens, so the
> exception gets thrown at the native->managed transition.
> Perhaps I'm oversimplifying this - maybe the thread abort code is too
> specific to thread abort, and I certainly don't want to butcher it. To me,
> so far, this looks like an opportunity to generalize code that was
> originally intended to be an exception [so to speak] to the way
> ThreadAbortException is thrown, compared to other exceptions.
> We're also not super-familiar with all of Mono's existing facilities for
> this stuff - if there is a straightforward function we should call and/or
> adapt to our environment, that'd be quite helpful too.
Now I see how and what you're trying to accomplish. Let's think in steps.
About OOM. The managed case is already handled for you, the unmanaged one
will require some environment help. But your plan of releasing some guard
then raising an OOM exception is sound.
To apply it to stack overflow is a bit trickier since you need to handle
the case where managed code is executing as well.
To handle native OOM, I guess patching the thread interruption code is the
easier way to go. Change mono_thread_interruption_checkpoint_request to
check for your OOM condition and you're set.
To handle stack overflow it will require a bit more work. You could
patch mono_thread_interruption_checkpoint_request to check for it as well.
But would still need to patch the stack with a trampoline to raise the
overflow exception in case it happens strictly on managed code.
And then you have a trickier issue, which is to reconquer soft guard pages
from stack and memory allocator. This is specially important in case of
-------------- next part --------------
An HTML attachment was scrubbed...
More information about the Mono-devel-list