Thanks for the detailed response Tom.
I understand the cause now.

> You might try to pre-allocate bitmap memory before launching the WebViews?
It's not the WebView that's triggering the OOM, but some arbitrary other
piece of code that needs memory that is not *there* anymore. Very often this
is happening when starting a new activity.

Ok, I see, I have to start dealing with automating my apology.

There is one more, small thing that I can do. I also do some downloading and
XML parsing in the background at times. This only takes Java Heap (<3MB),
but maybe I should move that stuff to a separate process. This may lower the
chances of an OOM. I'll think about it, but with all the added complexity of
inter process communication I am not sure I would want to go there.

Anyway, thanks for sharing your insights. That was very helpful.



On Wed, Oct 7, 2009 at 10:48 PM, Tom Gibara <[email protected]> wrote:

> I think it's better to add a couple more columns to the table to see the
> picture (as I see it) more clearly:
> JH = Java Heap
> JU = Memory actually used by Java
> NH = Native Heap
> TU = Total memory Used = JU + NH
> TA = Total memory Allocated = JH + NH
>
> (note I'm not distinguishing between native heap and native heap used
> because it's not relevant here)
>
> The system requires TA (the process size as you called it) to not exceed
> 16MB, the evolution is:
>
>     JU JH NH TU TA
>  1)  2  2  0  2  2
>  2)  4  4  0  4  4
>  3)  4  4  2  6  6
>  4) 14 14 2 16 16
>  5)  4 14  2  6 16
>  6)  4 14  4 10 18 *** OH NO! ***
>
> The key is what happens between (4) and (5): GC reclaims 10MB (JU reduced
> by 10MB) but the java heap doesn't shrink (JH stays at 14MB). This enlarged
> java heap basically squeezes the maximum native heap allocation.
>
> The simplest approach is to try and ensure that your application maintains
> a 'flatish' memory profile - no big spikes. You should do this anyway, since
> it means that your application is being well behaved and won't force other
> apps to be terminated just because your application needs a temporary shot
> of memory (which will then remain as a glut until the application restarts).
>
> As you point out, WebViews are heavy on memory usage, and these might be
> what's causing your memory usage to spike. I don't have any good suggestions
> for a fix. You might try to pre-allocate bitmap memory before launching the
> WebViews? It might work, but it may be complicated to do and could cause
> OOMs when WebViews are instantiated - no way around that, your application
> is simply using too much memory at that point.
>
> Tom
>
> 2009/10/7 Mariano Kamp <[email protected]>
>
>> Hi Tom, thanks for taking the time.
>>
>> On Wed, Oct 7, 2009 at 8:34 PM, Tom Gibara <[email protected]> wrote:
>>
>>>  1) Process starts up, generating a java heap allocation of 2MB.
>>>  2) Application initializes its state and allocates 2MB in the java heap.
>>>  3) Application creates a 2MB Bitmap which is allocated in the native
>>> heap
>>>  4) Application updates its state by crunching a 10MB byte array
>>>  5) Garbage collector kicks in and reclaims the 10MB byte array
>>>  6) Application attempts to a create a new 2MB Bitmap
>>>  7) An OutOfMemoryException is raised.
>>>
>>
>>  For the slow learners, like me:
>>
>> After Step) Java Heap, Native Heap, Process Size
>> 1) 2, 0, 2
>> 2) 4, 0, 4
>> 3) 4, 2, 6
>> 4) 14, 2, 16 (no the process is at its limit)
>> 5) 4, 2, 16
>> 6) Bang, because Native Heap needs to be grown by 2 MB, but the Process
>> Size reached its 16MB ceiling in step 4.
>> Is that it?
>>
>> And the Native Heap is in the same process as the Java Heap? I thought
>> before that the bitmaps reside in another process and my process is just
>> used for "accounting".
>>
>> Any good way to work around this? It doesn't happen all that often, but
>> two, three times a week I need to send an apology to users where this
>> happened? Either I have to automate the apology (a popup maybe?) or I can
>> fix the issue. But the latter doesn't seem that easy. For some sites WebView
>> really takes a lot of memory and I won't be able to "fix" that. And afaik I
>> can't signal the OS to please restart my process or can I?
>>
>> Cheers,
>> Mariano
>>
>>
>>
>>
>>> At first sight it looks as though the total memory usage at (6) is 6MB
>>> (4MB java and 2MB native) so the allocation should succeed. BUT (4) raised
>>> the Java heap size to 14MB, and though most of that is no longer in use, the
>>> java heap does not shrink. So the actual allocation to the native heap is
>>> only 2MB and that is already used by the first bitmap.
>>>
>>> I hope this is correct, perhaps someone else could corroborate it, I
>>> don't want to spread my misunderstandings.
>>>
>>> Tom
>>>
>>>
>>> 2009/10/7 Mariano Kamp <[email protected]>
>>>
>>> Hi,
>>>>
>>>>   I very often get bug reports about out-of-memory errors.
>>>>
>>>>   Those errors are caught bei the default exception handler where I then
>>>> ask how much memory is left (see below). Very often, like in the case from
>>>> below, there is plenty of memory left though.
>>>>
>>>>   I am wondering why this is?
>>>> Of course, it might be that the bitmap (bitmap size exceeds VM budget)
>>>> is actually megabytes and megabytes, but as these are resources that are
>>>> small (and used by all the other users that don't get ooms) I would say
>>>> that's not the case.
>>>> Maybe the memory has been freed between the error and the measurement.
>>>> That would be unfortunate. Any better wetter to measure the current memory
>>>> consumption?
>>>>
>>>>   Or am I missing something and there is a completely different
>>>> explanation? That would be wonderful and maybe give me a completely new
>>>> attack vector against those bugs.
>>>>
>>>>   FWIW. I embed WebView and it is one of my top candidates for huge
>>>> memory consumption. Maybe there is something I can measure?
>>>>
>>>> Cheers,
>>>> Mariano
>>>>
>>>> -- Time: Sat Oct 03 11:19:00 GMT+01:00 2009
>>>> -- Android Version: sdk=3, release=1.5, inc=150879
>>>> -- Memory free: 12.27MB total: 15.44MB max: 16.00MB
>>>> -- NewsRob Version: 3.1.0/310
>>>> -- Stacktrace:(3390)
>>>> android.view.InflateException: Binary XML file line #29: Error inflating
>>>> class java.lang.reflect.Constructor
>>>> at android.view.LayoutInflater.
>>>>
>>>> createView(LayoutInflater.java:512)
>>>> at
>>>> com.android.internal.policy.impl.PhoneLayoutInflater.onCreateView(PhoneLayoutInflater.java:56)
>>>> at
>>>> android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:562)
>>>> at android.view.LayoutInflater.rInflate(LayoutInflater.java:617)
>>>> at android.view.LayoutInflater.inflate(LayoutInflater.java:407)
>>>> at android.view.LayoutInflater.inflate(LayoutInflater.java:320)
>>>> at
>>>> android.widget.ResourceCursorAdapter.newView(ResourceCursorAdapter.java:79)
>>>> at
>>>> android.widget.SimpleCursorAdapter.newView(SimpleCursorAdapter.java:93)
>>>> at android.widget.CursorAdapter.getView(CursorAdapter.java:182)
>>>> at android.widget.AbsListView.obtainView(AbsListView.java:1269)
>>>> at android.widget.ListView.makeAndAddView(ListView.java:1623)
>>>> at android.widget.ListView.fillDown(ListView.java:607)
>>>> at android.widget.ListView.fillSpecific(ListView.java:1194)
>>>> at android.widget.ListView.layoutChildren(ListView.java:1459)
>>>> at android.widget.AbsListView.onLayout(AbsListView.java:1113)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.widget.FrameLayout.onLayout(FrameLayout.java:333)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.widget.FrameLayout.onLayout(FrameLayout.java:333)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.widget.LinearLayout.setChildFrame(LinearLayout.java:1119)
>>>> at android.widget.LinearLayout.layoutVertical(LinearLayout.java:998)
>>>> at android.widget.LinearLayout.onLayout(LinearLayout.java:918)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.widget.FrameLayout.onLayout(FrameLayout.java:333)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.widget.FrameLayout.onLayout(FrameLayout.java:333)
>>>> at android.view.View.layout(View.java:6133)
>>>> at android.view.ViewRoot.performTraversals(ViewRoot.java:929)
>>>> at android.view.ViewRoot.handleMessage(ViewRoot.java:1482)
>>>> at android.os.Handler.dispatchMessage(Handler.java:99)
>>>> at android.os.Looper.loop(Looper.java:123)
>>>> at android.app.ActivityThread.main(ActivityThread.java:3948)
>>>> at java.lang.reflect.Method.invokeNative(Native Method)
>>>> at java.lang.reflect.Method.invoke(Method.java:521)
>>>> at
>>>> com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:782)
>>>> at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:540)
>>>> at dalvik.system.NativeStart.main(Native Method)
>>>> Caused by: java.lang.reflect.InvocationTargetException
>>>> at android.widget.TextView.<init>(TextView.java:308)
>>>> at java.lang.reflect.Constructor.constructNative(Native Method)
>>>> at java.lang.reflect.Constructor.newInstance(Constructor.java:446)
>>>> at android.view.LayoutInflater.createView(LayoutInflater.java:499)
>>>> ... 37 more
>>>> Caused by: java.lang.OutOfMemoryError: bitmap size exceeds VM budget
>>>> at android.graphics.BitmapFactory.nativeDecodeAsset(Native Method)
>>>> at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:363)
>>>> at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:212)
>>>> at
>>>> android.graphics.drawable.Drawable.createFromResourceStream(Drawable.java:663)
>>>> at android.content.res.Resources.loadDrawable(Resources.java:1637)
>>>> at android.content.res.TypedArray.getDrawable(TypedArray.java:548)
>>>> at android.view.View.<init>(View.java:1725)
>>>> at android.widget.TextView.<init>(TextView.java:314)
>>>> ... 41 more
>>>>
>>>>
>>>>
>>>
>>>
>>>
>>
>>
>>
>
> >
>

--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google
Groups "Android Developers" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to
[email protected]
For more options, visit this group at
http://groups.google.com/group/android-developers?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to