Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it still the case that Android never unloads classes?

We have a large app that's always running into the dread method count limit. I've been asked to come up with a way to let it do much more, including supporting plugins. Looking for ways to unload code, I ran across JNI Tips which says

Classes are only unloaded if all classes associated with a ClassLoader can be garbage collected, which is rare but will not be impossible in Android.

This did seem to imply that a plugin can be unloaded if you, say,

  1. use a new DexClassLoader for each .jar file,
  2. only ever refer to the plugin through an interface reference, and
  3. null-out any copies of that interface reference when done.

So, I created a test case:

  1. I created a couple of trivial plugins, using a unique loader for each.
  2. I created a ReferenceQueue<ClassLoader> and created weak references to my two loaders, using that queue; I created/started a thread that loops indefinitely, doing a queue .remove() and reporting.
  3. I similarly created a ReferenceQueue<Class<?>> and created weak references to each plugin's getClass() using the queue; I created/started another thread monitoring the class reference queue.
  4. I create a thousand 1000x1000xARGB_8888 bitmaps to thoroughly force gc.

My monitoring threads seem to work - I saw loader2 get gc-ed when I used loader1 to load both plugins by mistake ;-) - but otherwise my threads stay silent, even on 4.3. Am I maybe missing something obvious in this test case, or is it still the case that the

Dalvik VM doesn't currently unload classes

as Google employee fadden says in Android: When do classes get unloaded by the system?

like image 691
Jon Shemitz Avatar asked Sep 17 '13 01:09

Jon Shemitz


1 Answers

The Dalvik VM still doesn't unload classes. The JNI Tips page is encouraging good behavior so your app doesn't break if the VM starts unloading classes someday.

like image 141
fadden Avatar answered Nov 15 '22 01:11

fadden