[JAVA] [JVM] OOM (Out Of Memory) Connaissances nécessaires pour le dépannage

introduction

Lors du traitement des échecs de MOO, j'ai visité de nombreux sites et des entrées répétées. À cette époque, j'avais beaucoup de mal à obtenir systématiquement des connaissances. J'ai donc écrit cet article en espérant qu'il serait utile pour ceux qui luttent de la même manière.

Si vous connaissez déjà JVM et souhaitez savoir comment gérer les problèmes de MOO, reportez-vous à cet article. [JVM] Défions la réponse en cas d'échec de MOO (mémoire insuffisante) ** Veuillez vérifier ici car il a été ajouté **

Public cible

・ JVM? Je ne sais pas ça! Gens ・ Ingénieurs qui ont les mêmes problèmes tels que MOO -Dieu de la destruction qui démarre un processus sans définir le journal JVM, etc.

Ce que vous pouvez obtenir de cet article

-Définir les options de démarrage minimales pour préparer la réponse à l'échec du MOO ・ Vous serez en mesure d'identifier la cause du MOO et de prendre des mesures pour le résoudre. ・ Sachez ce que vous devez absolument savoir sur Linux

Reçu une commande pour traiter les échecs du MOO

Il a fallu environ un mois pour réparer une certaine fonction. Après avoir testé et préparé la sortie, nous sommes prêts à sortir! À ce moment-là ** Un événement s'est produit au cours duquel les services répertoriés dans l'environnement de vérification ont été supprimés une fois par semaine. ** ** Je savais que la raison était Out Of Memory (OOM), mais je ne sais pas pourquoi cela s'est produit. De plus, il n'y a personne autour de moi qui soit familier avec JVM, et il n'y a pas de données telles que le vidage de tas (plus à ce sujet plus tard). Par exemple, je me sentais abandonné sur une île inhabitée avec mon ordinateur portable.

** J'ai entendu des mots comme JVM, GC, tas, mais je ne comprends pas le sens. J'ai décidé de résumer ce que j'ai appris pour résoudre ce problème de MOO dans cet article. ** **

Contribution

Tout d'abord, à partir de la section d'entrée. Il est impossible sans les connaissances nécessaires pour enquêter. Ici, nous allons nous concentrer sur l'apprentissage du fonctionnement de la JVM et du GC.

Qu'est-ce que JVM

En un mot, c'est le logiciel nécessaire pour exécuter les programmes Java. Ruby et Scala fonctionnent également sur JVM. La caractéristique de JVM est que le programme peut être exécuté indépendamment de la plate-forme. ** En d'autres termes, il peut fonctionner indépendamment de l'environnement OS (Windows, Mac, Linux, etc.). ** **

Configuration JVM

La JVM se voit attribuer la zone de mémoire du système d'exploitation au démarrage. Cela sera expliqué plus tard, mais il peut être défini par une option de démarrage (par exemple java -Xms100m).

La JVM a la structure suivante. JVM.png

Ces domaines seront décrits en détail ci-dessous.

Tas Java

** En un mot, la zone de mémoire utilisée par le programme créé par l'utilisateur. ** ** En d'autres termes, l'espace mémoire où sont stockés les objets et les tableaux utilisés dans les programmes Java. Je pense que j'instancie un objet lorsque j'exécute un programme, mais la mémoire est allouée à ce moment-là.

À proprement parler, le tas Java est divisé en nouvelle zone et ancienne zone.

Nouvelle zone

** La zone où l'objet nouvellement créé est stocké pour la première fois ** En fait, même dans la nouvelle zone, la zone est divisée en Eden et survivant. Les objets nouvellement créés, etc. sont d'abord stockés dans la zone Eden. Lorsque la mémoire de la zone Eden devient pleine, elle est stockée dans le Survivant (à proprement parler, «De la zone» et «Vers la zone») pour enregistrer l'objet.

J'expliquerai en détail plus tard, mais j'aimerais que vous le mettiez un peu dans le coin de votre tête. Scavenge GC est fait pour la nouvelle zone.

Ancien quartier

** Zone où les objets de longue durée sont stockés parmi les objets stockés dans la zone Nouveau. ** ** Une longue vie est un objet qui a été utilisé pendant longtemps dans le processus. Par exemple, un objet utilisé uniquement dans une méthode de traitement est un objet de courte durée.

puclic hoge() {
    Fuga fuga = new fuga();
}

J'expliquerai en détail plus tard, mais j'aimerais que vous le mettiez dans le coin de votre tête. ** Le GC complet est effectué sur la zone Old. ** **

Pas cher

L'espace mémoire que la JVM utilise pour exécuter des bibliothèques natives.

Zone permanente

Un espace mémoire où les informations de classe et de méthode sont stockées. Puisqu'il est stocké en premier, la taille ne change pas beaucoup.

Pile de fils

Zone de pile de threads Java

Comment fonctionne GC

Un mécanisme qui supprime les objets qui ne sont plus utilisés.

Pour ceux qui ne comprennent pas l'image, par exemple Tout d'abord, imaginez une rizière. Les semis sont plantés dans les rizières et une fois arrosés, ils deviennent du riz. (Image qui crée l'objet) Disons qu'il y a un gars qui se fait bousiller sur le chemin des semis au riz. (Image que l'objet n'est plus référencé) C'est le rôle du GC d'accueillir automatiquement la personne qui a échoué. Cela augmentera la superficie de plantation de nouveaux plants, ce qui est un mécanisme bienvenu pour les propriétaires de rizières.

Pour devenir un objet que le GC supprime, les points suivants doivent être respectés. ** - L'objet n'est référencé de nulle part. ** **

De plus, GC est grossièrement divisé en deux modèles. Scavenge GC (également appelé copie GC / GC mineur) et GC complet (également appelé GC majeur).

Scavenge GC L'objet généré est affecté à la nouvelle zone. ** Lorsque la nouvelle zone est pleine, le GC est effectué sur la nouvelle zone. ** ** Cela s'appelle Scavenge GC. Scavenge GC supprime les objets à supprimer, et les objets qui sont encore utilisés et qui ont une longue durée de vie sont déplacés vers la zone Ancien. De cette manière, la nouvelle zone est sécurisée et le nouvel objet est prêt à être accepté. C'est comme un séjour chez l'habitant à court terme.

Full GC ** Lorsque la zone Ancienne et la zone Parmanent sont pleines, le GC sera effectué pour la zone future. ** ** C'est Full GC.

Qu'est-ce que MOO?

Grosso modo Si l'une des zones présentées ci-dessus manque de mémoire, la machine virtuelle Java provoquera une erreur de mémoire insuffisante.

L'important ici est de déterminer où le MOO s'est produit. ** Tout d'abord, prendre une décision et identifier la zone devrait être la première chose dans le dépannage du MOO! !! !! !! !! ** **

Options de démarrage Java (il suffit de lire ici et de définir les options de démarrage vous aidera)

Seules les options minimales qui doivent être absolument expliquées. -Spécifier la taille du tas Java

-Xms -Xmx

-Xms est la taille initiale du tas Java. Généralement égal à -Xmx. -Xmx est la taille maximale du tas Java. Vous pouvez voir les informations ci-dessus lors du démarrage d'un processus Java avec la commande suivante.

ps aux | grep java

・ Vérifiez l'état d'occurrence du GC et l'état de fuite de mémoire

-verbose:gc(-Xloggc:Chemin du fichier répertorié ici)、-XX:+PrintGCTimeStamps、-XX:+PrintGCDetails

En définissant cela, les informations du journal GC seront affichées en détail. Si vous souhaitez voir le journal GC du processus Java en cours d'exécution, vérifiez-le avec la commande suivante.

#Vérifier le processus java
jcmd -l

#au dessus de<pid>Entrez pour vérifier le journal GC
jstat -gcutil -h10 <pid> 10000

-Obtenir un vidage de tas

-XX:+HeapDumpOnOutOfMemoryError

En définissant cela, le vidage du tas sera acquis lors de l'arrêt au MOO. ** Un vidage de tas est comme un instantané de l'état du tas. ** ** Étant donné que la taille du tas à un certain point est acquise, le taux d'utilisation de la mémoire peut être comparé en comparant immédiatement après le démarrage, un jour plus tard, etc. Il est facile de comprendre la transition et la cause.

De plus, si vous souhaitez tirer à tout moment, exécutez la commande suivante pour l'obtenir.

#Vérifier le processus java
jcmd -l

#au dessus de<pid>Pour obtenir un vidage de tas
jmap -dump:format=b,file=filename <pid>

Pour plus de détails, consultez ce lien. http://d.hatena.ne.jp/learn/touch/20090218/p1

Une fois résumé

C'est la fin de l'explication du mécanisme de JVM et du mécanisme de GC. Dans la mesure du possible, j'ai écrit cet article pour que je puisse systématiquement comprendre JVM et creuser dans les détails sur d'autres sites.

Production

Cela fait un peu trop longtemps, je vais donc le rassembler dans un autre article.

[JVM] Défions la réponse en cas d'échec de MOO (mémoire insuffisante)

Recommended Posts

[JVM] OOM (Out Of Memory) Connaissances nécessaires pour le dépannage
Attention à la valeur de retour de __len__