2012-02-21 6 views
10

La pregunta está básicamente contenida en el título.¿La JVM fuerza la recolección de basura cuando alcanza su límite de -Xmx?

Supongamos que tiene una aplicación que ha alcanzado su límite JVM -Xmx. Cuando esa aplicación requiere más memoria, ¿se fuerza la recolección de basura? (en el HotSpot JVM)

Una segunda cosa extraña que no puedo explicar es que actualmente tengo un servidor de aplicaciones que se ejecuta con -Xmx = 2048m, el comando "superior" (en Linux) informa 2.7g para su proceso.

Entonces, ¿cómo/cuándo se permite que una aplicación exceda su -Xmx?

Gracias,

+1

'-Xmx = 2048' es de 2048 bytes. Supongo que te refieres a '-Xmx = 2048m' Nota: Puedes escribir simplemente' -mx2g' que es lo mismo. –

+0

@PeterLawrey Gracias, sí, quise decir 2048m. Editado la pregunta. – Simeon

Respuesta

11

En realidad, el GC normal se activa cuando la generación joven está llena (no todo el montón) y el GC principal se activa cuando no queda espacio en el espacio del sobreviviente, por lo que algunos objetos deben migrarse a la generación anterior.

+2

+1: Por lo general, un espacio de duración completa es lo que desencadena un GC completo. Las colecciones menores usualmente evitan que el espacio del sobreviviente se llene moviendo objetos al espacio ocupado antes de que esto ocurra. –

+2

El '-Xmx' solo establece el tamaño máximo de almacenamiento dinámico. Esta suele ser la zona más grande, pero no la única. Tiene subprocesos de hilo, memoria directa, bibliotecas compartidas, la propia JVM, etc. –

1

Sí, si usted no tiene todavía encontrar la memoria que aumentará error OutofMemory. Lo entiendo así.

3

Suele ser el caso, aunque el GC normalmente se activa mucho antes, según el Recolector de basura que utilice.

1

IIRC la garantía es que se realizará un GC completo antes de que se genere un OutOfMemoryError. Debido a que exceder el límite del tamaño del montón debe generar un error de ese tipo, eso implica que siempre tendrá al menos una carrera completa del GC cuando se alcance el límite.

3

Sí, la JVM ciertamente llamará al GC si alcanza el límite del montón (y probablemente mucho antes). Si esto no ayuda, lanzará OutOfMemoryError s.

La razón por la que está viendo un mayor consumo de memoria de proceso es porque la opción -Xmx solo limita el espacio de almacenamiento dinámico de Java (donde se asignan los objetos de Java). Hay varias otras regiones de memoria utilizadas por la JVM adicionalmente: espacio para pilas de subprocesos, el "PermGen" (donde se almacenan las clases y su código), memoria "directa" asignada a través de ByteBuffers, memoria asignada por bibliotecas nativas, etc. Para algunos de estas regiones de memoria adicionales existen otras opciones de configuración que permiten limitarlas, por ejemplo -Xss, pero algunas incluso están fuera de control de la JVM.

0

La recolección de basura es una zona bastante grande, pero lo que dice es correcto para colecciones completas (hay otros tipos)

Una cosa a tener en cuenta es que -Xmx establece el tamaño máximo del montón, pero también hay an -Xms, que es el tamaño de pila mínimo. Su aplicación puede comenzar solo con el mínimo configurado. Luego, si la memoria utilizada llega a eso, activará una recolección de basura completa Y aumentará la cantidad de almacenamiento disponible, desde el mínimo (-Xmx) hasta algún valor menor o igual al máximo (-Xmx). Esto puede suceder varias veces, hasta alcanzar el máximo. Después de eso, ya no puede aumentar el montón, pero las recolecciones de basura continuarán cuando se alcance ese máximo.

7

El parámetro Xmx solo especifica el tamaño del montón. El proceso de Java requiere más memoria ya que el montón es solo una parte del proceso de Java, supongo que también tiene otras cosas que el proceso de Java contiene como bibliotecas nativas, el generador de perm y también las asignaciones de memoria nativas hechas por la aplicación.

He aquí un buen artículo que describe la asignación de memoria: http://www.ibm.com/developerworks/java/library/j-nativememory-linux/

Cuestiones relacionadas