I have a test project which demonstrates a memory leak caused by Admob 4.1.1.
The basic scenario is I have two activities and I switch back and forth between the main and the sub activity several times. I then switch to DDMS and force a few GCs. Then dump the HPROF and look at the historgram filtered by com.test* to see how many instances of the main and sub activity there are. My screenshots of the histogram are attached:
A leak!
I then commented out the ads in the xml and reran and there were no leaks:
No leak now
I have found some relevant posts to Admob leaks such as here: Android AdMob causes memory leak?
Here is a list of things I have tried to resolve the issue:
- Wait some amount of time and then force gc
- Do not load the ad in oncreate but spawn a thread to wait then load it
- Tried a previous version of Admob (the one not written by Google)
- Called adView.destroy() in the onDestroy() activity's method
- The unbinding from this link
Obviously none of these things helped.
Here is the test project I wrote:
(Be sure to set your own publisher id when you run the test project)
download test leak android project
If it makes a difference I'm tesing on my SGS2 with Cyanogenmod ROM.
Does this happen for other people when they run this project?
Does anyone know the cause a fix or a workaround?
Thanks
My app uses 80% of the allowed 16Mb and the AdView leaks at every orientation change (since android destroys and recreates the whole activity then). As a result I am out of memory after a dozen or so orientation changes giving me the dreaded:
10-08 10:14:47.178: ERROR/dalvikvm-heap(2876): 1440000-byte external allocation too large for this process.
10-08 10:14:47.178: ERROR/dalvikvm(2876): Out of memory: Heap Size=5191KB, Allocated=2877KB, Bitmap Size=18675KB
10-08 10:14:47.178: ERROR/GraphicsJNI(2876): VM won't let us allocate 1440000 bytes
or similar.
The increase in memory can easily be seen in eclipse by doing a debug run and opening Window > Open perspective > Other > DDMS, clicking the "update heap" icon and doing a Cause GC. The easiest way to check imho is the #Objects. If the orientation has changed from portrait to landscape and back, the number of Objects should be exactly the same (and without AdView it is).
I work around the memory leak by making the AdView static
and not calling the destroy
At least this prevents memory leaks between every orientation change.
Also I set request to null after using it. Don't know if that helps.
My solution
Yes, I build it all up dynamically. I use removeAllViews to remove all views from my (LinearLayout) container. Then I use addView to put them all back again. The ad is clickable. Is there perhaps some transparent view in front of it in your case?