Größe des virtuellen Java-Speichers größer als angefordert (oder erforderlich)

9

Ich führe eine Reihe von Jobs in einem Computercluster aus und sie werden getötet, wenn sie eine angeforderte Ressourcennutzung durchlaufen - eine dieser Anwendungen ist die Größe des virtuellen Speichers.

In meinem Java-Startbefehl verwende ich -Xmx8000m , um eine anfängliche Stapelgröße von 8 GB anzugeben. Ich habe noch nicht gesehen, dass die tatsächliche Speichernutzung meines Programms über 4 GB hinausgeht, wollte aber auf der sicheren Seite sein.

Wenn ich jedoch den Befehl top verwende, sehe ich eine virtuelle Speichergröße für meinen Java-Prozess von 12 GB - was genau an der Grenze des angeforderten virtuellen Speicherplatzes liegt. Ich kann meine angeforderte VM-Größe nicht erhöhen, da die Jobs bereits gesendet wurden und je länger ich nach der geplanten Zeit frage.

Erfordert Java konsistent mehr VM-Heapspeicher als angegeben? Ist dies eine konstante Menge oder eine konstante% oder Zufall? Kann der Heapspeicher über a) die angeforderte VM-Größe (8 GB) oder b) die zugewiesene VM-Größe (12 GB) anwachsen.

Bearbeiten: Jre-1.7.0-openjdk unter Linux verwenden

    
Zack Newsham 13.05.2015, 09:42
quelle

3 Antworten

7

Dieser Artikel gibt eine gute Analyse des Problems: Warum verbraucht mein Java-Prozess mehr Speicher als Xmx? Und der Autor bietet diese ungefähre Formel an:

%Vor%
  

Aber neben der von Ihrer Anwendung verbrauchten Speicherkapazität ist auch die JVM selbst   braucht auch etwas Ellbogenfreiheit.   - Müllsammlung.   - JIT-Optimierung.   - Off-Heap-Zuordnungen.   - JNI-Code.   - Metaspace.

Seien Sie aber vorsichtig, da es sowohl von der Plattform als auch von der JVM-Version abhängen kann.

    
Volatile 13.05.2015 10:12
quelle
4

Dies könnte an der Änderung des malloc-Verhaltens in glibc 2.10+ liegen, wo malloc jetzt per-thread-Speicherpools (Arenen) erstellt. Die Arena-Größe auf 64-Bit beträgt 64 MB. Nach der Verwendung von 8 Arenen auf 64-Bit setzt malloc die Anzahl der Arenen auf number_of_cpus * 8. Wenn Sie also eine Maschine mit vielen Prozessorkernen verwenden, wird die virtuelle Größe sehr schnell auf eine große Menge eingestellt, obwohl der eigentliche Speicher vorhanden ist verwendet (Bewohnergröße) ist viel kleiner.

Da Sie eine virtuelle Größe von 12 GB sehen, verwenden Sie wahrscheinlich einen 64-Bit-Rechner mit 24 Kernen oder HW-Threads, was 24 * 8 * 64 MB = 12 GB ergibt. Die Menge des zugewiesenen virtuellen Speichers hängt von der Anzahl der Kerne ab, und die Anzahl ändert sich abhängig von der Anzahl der Kerne auf der Maschine, an die der Job gesendet wird, sodass diese Überprüfung nicht sinnvoll ist.

Wenn Sie Hadoop oder Garn verwenden und den Wert erhalten, setzen Sie yarn.nodemanager.vmem-check-enabled in yarn-site.xml auf false .

Referenzen:

Siehe # 6 auf dieser Seite:

Ссылка

Hier finden Sie weitere Links zu dieser Seite:

Ссылка

Beachten Sie, dass dies auf dieser Stapelüberlaufseite bereits teilweise beantwortet wurde:

Container läuft über Speichergrenzen hinaus

    
jamesy 19.10.2015 03:29
quelle
0

Sie sind wirklich scharf darauf, das Problem zu untersuchen, und Sie sind auf Linux, dann überprüfen Sie die PID Ihres jvm-Prozesses und sehen Sie sich die Datei /proc/<PID>/smaps an. Dort finden Sie den gesamten Prozessspeicher des Betriebssystems - wie vom Kernel gesehen. Sie werden sehen, wie der Mach-Heap-Prozess (OS-Heap) verwendet wird, welche Speicherbereiche aus Dateien (Bibliotheken), ... usw. zugeordnet werden.

PS: Sie können auch verschiedene Tools, um die Smaps-Datei zu analysieren, im Internet ablegen.

    
ibre5041 13.05.2015 10:46
quelle

Tags und Links