2012-06-29 8 views
24

Actualmente estoy investigando problemas de recolección de basura con mi aplicación de Android, y tengo curiosidad por saber si GC_FOR_ALLOC es indicativo de un problema mayor que otros mensajes de GC, como GC_CONCURRENT.¿GC_FOR_ALLOC es más "grave" cuando se investiga el uso de la memoria?

Según tengo entendido, GC_CONCURRENT está haciendo lo que debe hacer el recolector de basura. El montón ha alcanzado un límite particular, mejor va a limpiar la memoria.

GC_FOR_ALLOC me sugiere que algo más serio está sucediendo si intento crear un objeto y no queda memoria para hacerlo.

¿Existe un nivel de prioridad o "seriedad" para los mensajes del GC?

+0

¿ha leído http://stackoverflow.com/questions/895444/java-garbage-collection-log-messages? los enlaces a los que se hace referencia en la respuesta aceptada pueden ayudarlo – kommradHomer

+0

@kommradHomer Gracias por la respuesta, pero no creo que se aplique aquí, ya que es la máquina virtual de dalvik la que hará el barrido de GC. Todavía encontré el enlace para ser informativo, si es denso, leer. –

Respuesta

53

En un sentido, GC_FOR_ALLOC es más grave que GC_CONCURRENT, porque GC_FOR_ALLOC significa que no había suficiente memoria libre para cumplir con una solicitud de asignación, por lo que una recolección de basura era necesario, mientras que GC_CONCURRENT sólo significa que la GC se sentía como correr, por lo general, porque la cantidad de memoria libre se volvió inferior a un determinado umbral después de una asignación.

Un GC_FOR_ALLOC es por sí mismo no es un signo de un problema en su aplicación, sin embargo:

  • aplicaciones Android comienzan con un pequeño montón que crece (hasta cierto punto) cuando las aplicaciones requieren más y más memoria, y Se realiza un GC_FOR_ALLOC antes de aumentar el tamaño del montón. En este caso, GC_FOR_ALLOC es perfectamente normal.
  • Si asigna memoria más rápido de lo que el GC concurrente tiene tiempo para liberarla, GC_FOR_ALLOC es inevitable. Y no hay nada intrínsecamente incorrecto en asignar memoria más rápido que el GC simultáneo puede liberar memoria.

Un tipo más grave de GC en Android es GC_BEFORE_OOM, que se realiza cuando una solicitud de asignación falla incluso después de GC_FOR_ALLOC y cuando la pila de aplicaciones ha crecido tan grande como se le permite ser. Cuando esto suceda, como último recurso, Dalvik intentará lanzar también SoftReferences, antes de hacer un último intento de asignar memoria y si eso falla lanza una excepción OutOfMemory.

Si tienes curiosidad de mirar el código de esta lógica, es en tryMalloc() en dalvik.git/vm/alloc/Heap.cpp

De todos modos, si no le importa, no creo que la búsqueda en la salida Logcat es la forma más eficaz de depurar sus problemas de recolección de basura. No sé qué problema específico está teniendo, pero ¿ha analizado herramientas como el Allocation Tracker en DDMS y el análisis de volcados de heap con la ayuda de la herramienta hprof-conv? (Consulte http://android-developers.blogspot.se/2011/03/memory-analysis-for-android.html, por ejemplo, para comenzar.)

+0

Gracias por su respuesta. Mi aplicación ha estado en la naturaleza por un tiempo y estamos trabajando para afinarla. Uno de los grandes gastos generales fue que el GC corrió hasta 30 veces en una ventana de 4 segundos. Simplemente parecía excesivo en realidad. Con alguna optimización, GC se ejecuta 6 veces ahora, pero FOR_ALLOC es la única llamada que se realiza. Pero eso tiene sentido ahora. –

Cuestiones relacionadas