I have the following code in an Activity. Ultimately, I'm trying to do frame animation but the GC is killing performance. I've tried explicit recycles but it makes no difference.
I'm also aware that I can reuse the bitmap with BitmapFactor.Options.inBitmap and that indeed resolves the issue but limits me to API >= 11 which is not an option.
This code merely illustrates the problem. It is not part of my app:
Log.d("GC_badness", "0: " + SystemClock.uptimeMillis());
Bitmap image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "1: " + SystemClock.uptimeMillis());
image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "2: " + SystemClock.uptimeMillis());
image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "3: " + SystemClock.uptimeMillis());
image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "4: " + SystemClock.uptimeMillis());
image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "5: " + SystemClock.uptimeMillis());
image = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);
Log.d("GC_badness", "6: " + SystemClock.uptimeMillis());
This results in the following log entries. Each bitmap load from a jpg resource results in at least 3 garbage collections and as many as 8. Most of the time they collect nothing or next to nothing. The heap isn't growing, even though there are multiple messages saying that it is. That also is quite confusing.
I'm stumped. I can't find a way to reuse my bitmap pre-API 11 and I can't live with the huge delays imposed by all of these useless garbage collections.
04-07 18:17:51.860: D/GC_badness(7510): 0: 360583998
04-07 18:17:51.900: D/dalvikvm(7510): GC_FOR_ALLOC freed 34K, 5% free 6320K/6595K, paused 32ms
04-07 18:17:51.900: I/dalvikvm-heap(7510): Grow heap (frag case) to 7.744MB for 1584016-byte allocation
04-07 18:17:51.950: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 5% free 7867K/8199K, paused 27ms
04-07 18:17:52.000: D/dalvikvm(7510): GC_CONCURRENT freed <1K, 5% free 7868K/8199K, paused 2ms+3ms
04-07 18:17:52.030: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 5% free 7868K/8199K, paused 31ms
04-07 18:17:52.030: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 704016-byte allocation
04-07 18:17:52.070: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 4% free 8555K/8903K, paused 37ms
04-07 18:17:52.070: D/dalvikvm(8107): GC_FOR_ALLOC freed 1464K, 39% free 17183K/27911K, paused 62ms
04-07 18:17:52.100: D/GC_badness(7510): 1: 360584238
04-07 18:17:52.100: D/dalvikvm(8189): GC_CONCURRENT freed 286K, 8% free 6917K/7495K, paused 17ms+3ms
04-07 18:17:52.110: D/dalvikvm(7510): GC_CONCURRENT freed 1546K, 22% free 7009K/8903K, paused 2ms+2ms
04-07 18:17:52.150: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 22% free 7008K/8903K, paused 32ms
04-07 18:17:52.150: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 1584016-byte allocation
04-07 18:17:52.200: D/dalvikvm(7510): GC_FOR_ALLOC freed 0K, 4% free 8555K/8903K, paused 37ms
04-07 18:17:52.250: D/dalvikvm(7510): GC_CONCURRENT freed <1K, 4% free 8555K/8903K, paused 2ms+2ms
04-07 18:17:52.280: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 4% free 8555K/8903K, paused 30ms
04-07 18:17:52.280: I/dalvikvm-heap(7510): Grow heap (frag case) to 9.086MB for 704016-byte allocation
04-07 18:17:52.310: D/dalvikvm(7510): GC_FOR_ALLOC freed 0K, 4% free 9243K/9607K, paused 23ms
04-07 18:17:52.330: D/dalvikvm(8107): GC_CONCURRENT freed 588K, 34% free 18618K/27911K, paused 4ms+5ms
04-07 18:17:52.350: D/GC_badness(7510): 2: 360584482
04-07 18:17:52.350: D/dalvikvm(7510): GC_CONCURRENT freed 1546K, 20% free 7696K/9607K, paused 1ms+2ms
04-07 18:17:52.380: D/dalvikvm(7510): GC_FOR_ALLOC freed 688K, 28% free 7008K/9607K, paused 22ms
04-07 18:17:52.380: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 1584016-byte allocation
04-07 18:17:52.400: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 11% free 8555K/9607K, paused 21ms
04-07 18:17:52.440: D/GC_badness(7510): 3: 360584577
04-07 18:17:52.450: D/dalvikvm(7510): GC_CONCURRENT freed <1K, 4% free 9243K/9607K, paused 1ms+2ms
04-07 18:17:52.470: D/dalvikvm(7510): GC_FOR_ALLOC freed 2234K, 28% free 7008K/9607K, paused 20ms
04-07 18:17:52.470: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 1584016-byte allocation
04-07 18:17:52.500: D/dalvikvm(7510): GC_FOR_ALLOC freed 0K, 11% free 8555K/9607K, paused 29ms
04-07 18:17:52.510: D/dalvikvm(8107): GC_CONCURRENT freed 1785K, 33% free 18832K/27911K, paused 2ms+5ms
04-07 18:17:52.530: D/GC_badness(7510): 4: 360584668
04-07 18:17:52.540: D/dalvikvm(7510): GC_CONCURRENT freed <1K, 4% free 9243K/9607K, paused 1ms+2ms
04-07 18:17:52.570: D/dalvikvm(7510): GC_FOR_ALLOC freed 2234K, 28% free 7008K/9607K, paused 28ms
04-07 18:17:52.570: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 1584016-byte allocation
04-07 18:17:52.590: D/dalvikvm(7510): GC_FOR_ALLOC freed <1K, 11% free 8555K/9607K, paused 22ms
04-07 18:17:52.620: D/dalvikvm(7510): GC_CONCURRENT freed <1K, 4% free 9243K/9607K, paused 3ms+2ms
04-07 18:17:52.630: D/GC_badness(7510): 5: 360584765
04-07 18:17:52.650: D/dalvikvm(7510): GC_FOR_ALLOC freed 2235K, 28% free 7008K/9607K, paused 21ms
04-07 18:17:52.650: I/dalvikvm-heap(7510): Grow heap (frag case) to 8.416MB for 1584016-byte allocation
04-07 18:17:52.680: D/dalvikvm(7510): GC_FOR_ALLOC freed 0K, 11% free 8555K/9607K, paused 27ms
04-07 18:17:52.710: D/GC_badness(7510): 6: 360584844
Why do you want to reuse the image?
Dont give the garbage collector a chance to collect something. Basically every object you define locally will sooner or later be collected.
Do not reuse your image Variable. Make a imagearray and the images prior your animation code (best would be, to load during the actiity is created).
Or consider to use an ObjectPool for your images.
Here is a good SO answer on how to aboid Garbage collection.
And finally you can find plenty of information on how to avoid Garbage collection when you google for eg. "how to avoid garbage collection android".
Related
I am creating Image apps which has over 4k images. I dont load images as required rather load when required however if user visits different parts of app which links to different images my app becomes slow and waits for GC to run which makes it bad user experience.
I saw logcat with following messages:
10-08 14:21:26.249: D/dalvikvm(31547): GC_FOR_ALLOC freed 1677K, 13% free 14097K/16124K, paused 29ms, total 29ms
10-08 14:21:26.749: D/dalvikvm(31547): GC_FOR_ALLOC freed 1711K, 13% free 14092K/16124K, paused 28ms, total 28ms
10-08 14:21:27.610: D/dalvikvm(31547): GC_FOR_ALLOC freed 1694K, 13% free 14103K/16124K, paused 29ms, total 29ms
10-08 14:21:29.592: D/dalvikvm(31547): GC_FOR_ALLOC freed 1729K, 13% free 14081K/16124K, paused 32ms, total 32ms
10-08 14:21:30.874: D/dalvikvm(31547): GC_FOR_ALLOC freed 1675K, 13% free 14102K/16124K, paused 30ms, total 30ms
10-08 14:21:32.435: D/dalvikvm(31547): GC_FOR_ALLOC freed 1735K, 13% free 14075K/16124K, paused 33ms, total 33ms
10-08 14:21:34.017: D/dalvikvm(31547): GC_FOR_ALLOC freed 1629K, 13% free 14145K/16124K, paused 28ms, total 29ms
10-08 14:21:35.098: D/dalvikvm(31547): GC_FOR_ALLOC freed 1774K, 13% free 14093K/16124K, paused 29ms, total 29ms
10-08 14:21:36.290: D/dalvikvm(31547): GC_FOR_ALLOC freed 1703K, 13% free 14094K/16124K, paused 29ms, total 29ms
10-08 14:21:37.991: D/dalvikvm(31547): GC_FOR_ALLOC freed 1722K, 13% free 14077K/16124K, paused 27ms, total 28ms
10-08 14:21:39.213: D/dalvikvm(31547): GC_FOR_ALLOC freed 1693K, 13% free 14083K/16124K, paused 28ms, total 28ms
10-08 14:21:41.175: D/dalvikvm(31547): GC_FOR_ALLOC freed 1696K, 13% free 14088K/16124K, paused 28ms, total 28ms
I tried to improve/optimize my code by doing following changes:
Everytime I load app I clear my cached images.
Implemented ViewHolder pattern for ListViews.
Used android:largeHeap="true" attribute in Manifest at Application tag level.
Made classes which are used frequently to do some operations singleton.
But still not able to achieve performance i need.
I used Universal Image Loader Library which has cache mechanism but still its runs GC.
How to avoid GC or what are other optimization techniques.
I have exit my app, but there is still a backgroud service is running. Whe the GC logs come a log. I will so you the logs beblow. You can see, about 3 logs per second. Is This phenomenon is normal ? My device's memory is enough, and the backgroud service is holding a WebSocket connection.
08-11 10:33:54.456 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2020K, 18% free 10682K/12871K, paused 12ms+6ms, total 44ms
08-11 10:33:54.776 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1985K, 18% free 10676K/12871K, paused 12ms+8ms, total 54ms
08-11 10:33:55.109 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1950K, 18% free 10671K/12871K, paused 12ms+17ms, total 68ms
08-11 10:33:55.459 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2004K, 18% free 10680K/12871K, paused 13ms+8ms, total 62ms
08-11 10:33:55.769 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2010K, 18% free 10680K/12871K, paused 12ms+7ms, total 48ms
08-11 10:33:56.093 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1996K, 18% free 10677K/12871K, paused 12ms+9ms, total 50ms
08-11 10:33:56.416 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2028K, 18% free 10681K/12871K, paused 2ms+8ms, total 37ms
08-11 10:33:56.746 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2031K, 18% free 10682K/12871K, paused 8ms+8ms, total 46ms
08-11 10:33:57.079 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1996K, 18% free 10677K/12871K, paused 12ms+7ms, total 46ms
08-11 10:33:57.429 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2002K, 18% free 10678K/12871K, paused 12ms+19ms, total 59ms
08-11 10:33:57.766 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2003K, 18% free 10679K/12871K, paused 12ms+7ms, total 46ms
08-11 10:33:58.143 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1945K, 18% free 10669K/12871K, paused 12ms+17ms, total 72ms
08-11 10:33:58.473 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2020K, 18% free 10682K/12871K, paused 2ms+6ms, total 41ms
08-11 10:33:58.786 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2013K, 17% free 10690K/12871K, paused 12ms+8ms, total 48ms
08-11 10:33:59.106 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2031K, 18% free 10683K/12871K, paused 12ms+8ms, total 53ms
08-11 10:33:59.443 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2021K, 18% free 10681K/12871K, paused 12ms+8ms, total 48ms
08-11 10:33:59.786 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 2028K, 18% free 10681K/12871K, paused 11ms+7ms, total 44ms
08-11 10:34:00.153 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕ GC_CONCURRENT freed 1997K, 18% free 10677K/12871K, paused 12ms+18ms, total 58ms
Is This phenomenon is normal ?
It depends what you mean by "normal".
If you mean normal for an application with those particular heap dimensions, that amount of heapspace used for long-lived objects, and that rate of allocation ... then the answer is "Yes, it is normal".
Basically, you are running your application with a heap that is (objectively) too small for the work that you are asking it to do. You have roughly 2Mb of free space, and you are allocating objects at roughly 6Gb per second. If you want to reduce the number of GC cycles, you need to do one or more of the following:
Increase the heap size. (I don't know if this is feasible for an Android app ...)
Reduce the "working set" of long-lived objects. Maybe you have a memory leak, lots of large images loaded, or an overly large in-memory cache of ... something.
Reduce the rate at which new objects are being allocated by your application.
The last two require you to track down the source of the memory usage / allocation, and change you code to mitigate the effects. There are tools (memory profilers) that can help with this, but the details will be specific to your application.
Here's how I'd interpret the GC log lines ... by example:
08-11 10:33:54.456 6821-6823/com.tong.iknow:ik_service_v1 E/dalvikvm﹕
GC_CONCURRENT freed 2020K, 18% free 10682K/12871K, paused 12ms+6ms, total 44ms
The "GC_CONCURRENT" collector is being used.
This GC collection cycle reclaimed 2020K bytes.
When the GC cycle completed, 18% of the heap is free, and 10682K out of a total usable heap size of 12871K is in use.
Normal thread activity was paused for two intervals of 12ms and 6ms respectively.
The elapsed time for the GC cycle was 44ms.
Note that the amount of heap freed isn't always exactly the same as the different between total and available ... because for much of the time that the GC is running there are normal threads allocating new objects.
I am working on an application. In which I stuck in a problem. My problem is that when I am calling startActivity(intent) then it's not working and my logcat shows
!!! FAILED BINDER TRANSACTION!!!
Please help me out this problem.
Thanks
My code is
listview3.setOnItemClickListener(new OnItemClickListener()
{
public void onItemClick(AdapterView<?> arg0, View view, int arg2,
long arg3)
{
LinearLayout linear = (LinearLayout)view.findViewById(R.id.linearlist);
selected_section_id=webservice_sectionid.get(arg2);
selected_section_heading=webservice_sectionheading.get(arg2);
selected_section_no=webservice_sectionno.get(arg2);
String[] array_sectionid = new String[webservice_sectionid.size()];
String[] array_sectionheading = new String[webservice_sectionheading.size()];
String[] array_sectionno = new String[webservice_sectionno.size()];
String noofpage=String.valueOf(webservice_sectionno.size());
Intent intent = null;
intent=new Intent(Ruleservice1.this,SectionWebPage1.class);
intent.putExtra("SectionId", selected_section_id);
intent.putExtra("SectionHeading", selected_section_heading);
intent.putExtra("ActId", selectedvalue_id);
intent.putExtra("SelectListPosition", String.valueOf(arg2));
intent.putExtra("ActId_g", (ArrayList<String>) webservice_global_actid);
intent.putExtra("ActHeading_g", (ArrayList<String>) webservice_global_actheading);
intent.putExtra("SectionId1", selected_section_id1);
intent.putExtra("SectionNo", selected_section_no);
intent.putExtra("SectionNo1", selected_section_no1);
intent.putExtra("ActHeading", selectedvalue_heading);
intent.putExtra("array_sectionid", (ArrayList<String>) webservice_sectionid);
intent.putExtra("array_sectionheading", (ArrayList<String>) webservice_sectionheading);
intent.putExtra("array_sectionno", (ArrayList<String>) webservice_sectionno);
intent.putExtra("arrayActId", (ArrayList<String>)webservice_actid);
intent.putExtra("arrayActHeading", (ArrayList<String>)webservice_actheading);
intent.putExtra("flag", "0");
intent.putExtra("offlineStatus", offlineflag+"");
intent.putExtra("count", "Page "+String.valueOf(arg2+1)+" of "+ webservice_sectionno.size());
intent.putExtra("fromwhichpage", "rule");
intent.putExtra("noofpage", noofpage);
intent.putExtra("searchtext", SearchText);
intent.putExtra("hideshowtext", "Show");
intent.putExtra("arrayActCatid", selectedcatid);
startActivity(intent);
}
});
My Logcat
10-10 13:02:23.453: D/dalvikvm(2527): GC_CONCURRENT freed 3009K, 31% free 11791K/17031K, paused 2ms+3ms
10-10 13:02:23.563: D/dalvikvm(2527): GC_FOR_ALLOC freed 4K, 31% free 11790K/17031K, paused 26ms
10-10 13:02:23.573: I/dalvikvm-heap(2527): Grow heap (frag case) to 15.275MB for 3738592-byte allocation
10-10 13:02:23.643: D/dalvikvm(2527): GC_CONCURRENT freed 0K, 26% free 15441K/20743K, paused 2ms+3ms
10-10 13:02:23.663: D/dalvikvm(2527): GC_FOR_ALLOC freed 4544K, 48% free 10898K/20743K, paused 27ms
10-10 13:02:23.673: I/dalvikvm-heap(2527): Grow heap (frag case) to 14.403MB for 3738642-byte allocation
10-10 13:02:23.733: D/dalvikvm(2527): GC_FOR_ALLOC freed <1K, 30% free 14548K/20743K, paused 26ms
10-10 13:02:23.743: I/dalvikvm-heap(2527): Grow heap (frag case) to 19.751MB for 5607958-byte allocation
10-10 13:02:23.803: D/dalvikvm(2527): GC_CONCURRENT freed 3651K, 38% free 16374K/26247K, paused 1ms+4ms
10-10 13:02:23.833: D/dalvikvm(2527): GC_FOR_ALLOC freed 0K, 38% free 16374K/26247K, paused 29ms
10-10 13:02:23.843: I/dalvikvm-heap(2527): Grow heap (frag case) to 19.751MB for 3738646-byte allocation
10-10 13:02:23.903: D/dalvikvm(2527): GC_FOR_ALLOC freed <1K, 24% free 20025K/26247K, paused 28ms
10-10 13:02:23.913: I/dalvikvm-heap(2527): Grow heap (frag case) to 23.317MB for 3738700-byte allocation
10-10 13:02:23.973: D/dalvikvm(2527): GC_CONCURRENT freed 5476K, 40% free 18199K/29959K, paused 2ms+4ms
10-10 13:02:24.013: D/dalvikvm(2527): GC_FOR_ALLOC freed 3651K, 52% free 14548K/29959K, paused 31ms
10-10 13:02:24.023: I/dalvikvm-heap(2527): Grow heap (frag case) to 19.751MB for 5608046-byte allocation
10-10 13:02:24.093: D/dalvikvm(2527): GC_FOR_ALLOC freed 3651K, 54% free 16374K/35463K, paused 30ms
10-10 13:02:24.123: D/dalvikvm(2527): GC_FOR_ALLOC freed 0K, 54% free 16374K/35463K, paused 32ms
10-10 13:02:24.133: I/dalvikvm-heap(2527): Grow heap (frag case) to 19.751MB for 3738702-byte allocation
10-10 13:02:24.203: D/dalvikvm(2527): GC_CONCURRENT freed 129K, 44% free 19896K/35463K, paused 2ms+4ms
10-10 13:02:24.503: D/dalvikvm(2527): GC_CONCURRENT freed 5969K, 56% free 15957K/35463K, paused 2ms+5ms
10-10 13:02:24.803: D/dalvikvm(2527): GC_CONCURRENT freed 507K, 51% free 17497K/35463K, paused 2ms+5ms
10-10 13:02:25.143: D/dalvikvm(2527): GC_CONCURRENT freed 476K, 47% free 19115K/35463K, paused 3ms+6ms
10-10 13:02:25.473: D/dalvikvm(2527): GC_CONCURRENT freed 508K, 42% free 20684K/35463K, paused 2ms+6ms
10-10 13:02:25.813: D/dalvikvm(2527): GC_CONCURRENT freed 476K, 38% free 22256K/35463K, paused 2ms+6ms
10-10 13:02:26.163: D/dalvikvm(2527): GC_CONCURRENT freed 501K, 33% free 23796K/35463K, paused 2ms+6ms
10-10 13:02:26.553: D/dalvikvm(2527): GC_CONCURRENT freed 915K, 30% free 24981K/35463K, paused 2ms+7ms
10-10 13:02:28.643: E/JavaBinder(2527): !!! FAILED BINDER TRANSACTION !!!
Two things: intent.putExtra("searchtext", SearchText); looks wrong, probably a copy paste error?
Also, make sure that you don't put a lot of data into the Intent. String values and Integers are fine but you seem to be passing application data with ArrayLists, that's not how you transport information from one Activity to the other. You should either put them in a database and only transfer the relevant ids or store them in some cache that you an reference from every activity (like the application object).
Also check the link that Tim posted.
i just found this -> Failed binder transaction when putting an bitmap dynamically in a widget
In this Post they say this error is because of to big data.
I do not know if this will be the same reason, but try if the error also occurs if u pass less data with the intent.
In my link above, they write about a limit of 1 MB.
And btw sorry for my bad english. =)
in my simple app i am using 6 buttons and setting background with png.
Button btnGadgetmusic = (Button) findViewById(R.id.gadgetmusic);
btnGadgetmusic.setBackgroundResource(R.drawable.btnselectedsong);
minimum size of png is 13.5K and maximum size is 40K. When ever i try to run this app on emulator with version 2.3, i get "external allocation too large for this process" and interestningly if i run on honeycomb or on ICS then there is no problem.
So i am confused what should i do, should i ignore it, if not, do we have some better solution for that.
looking for your reply
EDIT Log File added
I/dalvikvm-heap(4190): Clamp target GC heap from 25.494MB to 24.000MB
D/dalvikvm(4190): GC_FOR_MALLOC freed <1K, 51% free 2647K/5379K, external 18806K/20812K, paused 28ms
D/dalvikvm(4190): GC_EXTERNAL_ALLOC freed <1K, 51% free 2647K/5379K, external 18806K/20812K, paused 49ms
I/dalvikvm-heap(4190): Clamp target GC heap from 25.833MB to 24.000MB
D/dalvikvm(4190): GC_FOR_MALLOC freed 0K, 51% free 2647K/5379K, external 19153K/20812K, paused 25ms
D/dalvikvm(4190): GC_EXTERNAL_ALLOC freed <1K, 51% free 2657K/5379K, external 19153K/20812K, paused 56ms
I/dalvikvm-heap(4190): Clamp target GC heap from 25.852MB to 24.000MB
D/dalvikvm(4190): GC_FOR_MALLOC freed <1K, 51% free 2657K/5379K, external 19162K/20812K, paused 24ms
D/dalvikvm(4190): GC_EXTERNAL_ALLOC freed 4K, 51% free 2671K/5379K, external 19162K/20812K, paused 69ms
I/dalvikvm-heap(4190): Clamp target GC heap from 25.887MB to 24.000MB
D/dalvikvm(4190): GC_FOR_MALLOC freed 0K, 51% free 2671K/5379K, external 19184K/20812K, paused 28ms
W/KeyCharacterMap(4190): No keyboard for id 0
W/KeyCharacterMap(4190): Using default keymap: /system/usr/keychars/qwerty.kcm.bin
W/KeyCharacterMap(4190): No keyboard for id 0
W/KeyCharacterMap(4190): Using default keymap: /system/usr/keychars/qwerty.kcm.bin
I/dalvikvm-heap(4190): Clamp target GC heap from 25.913MB to 24.000MB
D/dalvikvm(4190): GC_CONCURRENT freed 16K, 50% free 2697K/5379K, external 19184K/20812K, paused
3ms+35ms
I/dalvikvm-heap(4190): Clamp target GC heap from 25.942MB to 24.000MB
D/dalvikvm(4190): GC_CONCURRENT freed 13K, 50% free 2727K/5379K, external 19184K/20812K, paused 3ms+3ms
D/dalvikvm(4190): GC_EXTERNAL_ALLOC freed 2K, 50% free 2724K/5379K, external 19184K/20812K, paused 65ms
E/dalvikvm-heap(4190): 20736-byte external allocation too large for this process.
I/dalvikvm-heap(4190): Clamp target GC heap from 25.939MB to 24.000MB
E/GraphicsJNI(4190): VM won't let us allocate 20736 bytes
D/dalvikvm(4190): GC_FOR_MALLOC freed 0K, 50% free 2724K/5379K, external 19184K/20812K, paused 38ms
D/skia(4190): --- decoder->decode returned false
D/AndroidRuntime(4190): Shutting down VM
W/dalvikvm(4190): threadid=1: thread exiting with uncaught exception (group=0x40015560)
E/AndroidRuntime(4190): FATAL EXCEPTION: main
E/AndroidRuntime(4190): java.lang.OutOfMemoryError: bitmap size exceeds VM budget
Why does Android system always call garbage collection every time I make a request to web server to get images? Although I did every actions are asynchronous. Calling GC too many times make my app delays when scrolling or fling.
Update: I guess Android system always call GC when you do something request to web server. Here is the log when using the Android default browser. Each time you click on a link GC will be called automatically.
03-08 16:36:19.530: D/dalvikvm(341): GC_FOR_ALLOC freed 2124K, 31% free 10780K/15623K, paused 49ms
03-08 16:36:19.590: D/dalvikvm(341): GC_FOR_ALLOC freed 0K, 20% free 12635K/15623K, paused 49ms
03-08 16:36:19.700: D/dalvikvm(341): GC_CONCURRENT freed 1K, 20% free 12635K/15623K, paused 3ms+4ms
03-08 16:36:22.610: D/dalvikvm(20845): GC_CONCURRENT freed 735K, 10% free 9018K/9991K, paused 2ms+6ms
03-08 16:36:25.620: D/dalvikvm(20845): GC_CONCURRENT freed 1046K, 12% free 8954K/10119K, paused 4ms+3ms
03-08 16:36:27.880: D/dalvikvm(2781): GC_EXPLICIT freed 263K, 7% free 6373K/6791K, paused 2ms+2ms
03-08 16:36:28.950: D/dalvikvm(20845): GC_CONCURRENT freed 884K, 12% free 8946K/10119K, paused 3ms+3ms
03-08 16:36:29.760: D/dalvikvm(20845): GC_CONCURRENT freed 861K, 12% free 8949K/10119K, paused 3ms+3ms
03-08 16:36:31.390: D/dalvikvm(285): GC_EXPLICIT freed 1275K, 38% free 20843K/33223K, paused 17ms+8ms
03-08 16:36:31.510: D/dalvikvm(20845): GC_CONCURRENT freed 810K, 12% free 8946K/10119K, paused 3ms+5ms
03-08 16:36:38.100: D/dalvikvm(20845): GC_CONCURRENT freed 730K, 11% free 9027K/10119K, paused 3ms+6ms
03-08 16:36:40.920: D/dalvikvm(20845): GC_CONCURRENT freed 864K, 12% free 8989K/10119K, paused 2ms+5ms
03-08 16:36:45.780: D/dalvikvm(20845): GC_FOR_ALLOC freed 620K, 12% free 8909K/10119K, paused 41ms
03-08 16:36:48.250: D/dalvikvm(20845): GC_FOR_ALLOC freed 499K, 12% free 9002K/10119K, paused 45ms
03-08 16:36:48.570: D/dalvikvm(20845): GC_FOR_ALLOC freed 225K, 13% free 8899K/10119K, paused 28ms
03-08 16:36:50.670: D/dalvikvm(20845): GC_FOR_ALLOC freed 388K, 12% free 8915K/10119K, paused 34ms
03-08 16:36:52.550: D/dalvikvm(20845): GC_FOR_ALLOC freed 511K, 11% free 9008K/10119K, paused 44ms
03-08 16:36:53.780: D/dalvikvm(20845): GC_FOR_ALLOC freed 273K, 12% free 8909K/10119K, paused 42ms
03-08 16:37:05.070: D/dalvikvm(569): GC_EXPLICIT freed 376K, 12% free 6207K/6983K, paused 2ms+2ms
03-08 16:37:25.550: D/dalvikvm(2549): GC_CONCURRENT freed 337K, 9% free 7198K/7879K, paused 2ms+3ms
03-08 16:37:31.330: D/dalvikvm(2549): GC_EXPLICIT freed 54K, 10% free 7143K/7879K, paused 7ms+2ms
03-08 16:38:45.630: D/dalvikvm(2549): GC_EXPLICIT freed 268K, 10% free 7161K/7879K, paused 7ms+2ms
Android GC is automatic, opaque, non-deterministic. Which means you have nothing can do on it.
Traditionally, this type of GC works like this.
Wait until enough garbages are generated.
If GC engine thinks it's time, it stops your app.
Clear the garbages
Resume your app.
Of course, this sucks for end-use UI and graphics.
So Google added incremental collection. Essentially, this is just doing above procedure more frequently with less garbages. So pause time itself would be short but collection itself happens a lot more frequently.
As a conclusion, garbage collection happens randomly, but very frequently. So it would look happening always for any of operations.
Practically, there's no guaranteed way to avoid GC lag on typical GC systems.