259 votes

Comment obtenir un vidage des threads et du tas d'un processus Java sous Windows qui n'est pas exécuté dans une console ?

J'ai une application Java que je lance à partir d'une console qui, à son tour, exécute un autre processus Java. Je veux obtenir un vidage de thread/heap de ce processus enfant.

Sous Unix, je pouvais faire un kill -3 <pid> mais sous Windows, la seule façon d'obtenir un vidage de fil est de faire Ctrl-Break dans la console. Mais cela ne me donne que le vidage du processus parent, pas du processus enfant.

Y a-t-il un autre moyen d'obtenir ce vidage de tas ?

2voto

iny Points 3925

1voto

Darron Points 13196

Ver www.adaptj.com pour un utilitaire commercial qui vous permettra de générer des vidages de pile sous Windows. Il semble qu'il soit gratuit dans de nombreuses situations.

1voto

Le code java ci-dessous est utilisé pour obtenir le Heap Dump d'un processus Java en fournissant le PID d'un processus distant. Le programme utilise une connexion JMX à distance pour vider le tas dans un fichier. Cela peut être utile pour quelqu'un. Ne nécessite pas jmap.

import java.lang.management.ManagementFactory;
import javax.management.MBeanServerConnection;
import javax.management.remote.JMXConnector;
import javax.management.remote.JMXConnectorFactory;
import javax.management.remote.JMXServiceURL;
import java.lang.reflect.Method;

public class HeapDumper {

public static final String HOST = "192.168.11.177";
public static final String PORT = "1600";
public static final String FILE_NAME = "heapDump.hprof";
public static final String FOLDER_PATH = "C:/";
private static final String HOTSPOT_BEAN_NAME ="com.sun.management:type=HotSpotDiagnostic";

public static void main(String[] args) {
    if(args.length == 0) {
        System.out.println("Enter PID of the Java Process !!!");
        return;
    }

    String pidString = args[0];
    int pid = -1;
    if(pidString!=null && pidString.length() > 0) {
        try {
            pid = Integer.parseInt(pidString);
        }
        catch(Exception e) {
            System.out.println("PID is not Valid !!!");
            return;
        }
    }
    boolean isHeapDumpSuccess = false;
    boolean live = true;
    if(pid > 0) {
        MBeanServerConnection beanServerConn = getJMXConnection();

        if(beanServerConn!=null) {
            Class clazz = null;
            String dumpFile = FOLDER_PATH+"/"+FILE_NAME;
            try{
                clazz = Class.forName("com.sun.management.HotSpotDiagnosticMXBean");
                Object hotspotMBean = ManagementFactory.newPlatformMXBeanProxy(beanServerConn, HOTSPOT_BEAN_NAME, clazz);
                Method method = clazz.getMethod("dumpHeap", new Class[]{String.class , boolean.class});
                method.setAccessible(true);
                method.invoke(hotspotMBean , new Object[] {dumpFile, new Boolean(live)});
                isHeapDumpSuccess = true;
            }
            catch(Exception e){
                e.printStackTrace();
                isHeapDumpSuccess = false;
            }
            finally{
                clazz = null;
            }
        }
    }

    if(isHeapDumpSuccess){
        System.out.println("HeapDump is Success !!!");
    }
    else{
        System.out.println("HeapDump is not Success !!!");
    }
}

private static MBeanServerConnection getJMXConnection() {
    MBeanServerConnection mbeanServerConnection = null;
    String urlString = "service:jmx:rmi:///jndi/rmi://" + HOST + ":" + PORT + "/jmxrmi";
    try {
        JMXServiceURL url = new JMXServiceURL(urlString);
        JMXConnector jmxConnector = JMXConnectorFactory.connect(url);
        mbeanServerConnection = jmxConnector.getMBeanServerConnection();
        System.out.println("JMX Connection is Success for the URL :"+urlString);
    }
    catch(Exception e) {
        System.out.println("JMX Connection Failed !!!");
    }
    return mbeanServerConnection;
}

}

1voto

Stas S Points 80

Peut-être jcmd ?

Jcmd L'utilitaire est utilisé pour envoyer des demandes de commandes de diagnostic à la JVM, ces demandes étant utiles pour contrôler les enregistrements de vol Java, dépanner et diagnostiquer la JVM et les applications Java.

L'outil jcmd a été introduit avec Java 7 d'Oracle et est particulièrement utile pour résoudre les problèmes liés aux applications JVM. Il permet d'identifier les ID des processus Java (comme jps), d'obtenir des vidages de tas (comme jmap), d'obtenir des vidages de threads (comme jstack), d'afficher les caractéristiques de la machine virtuelle telles que les propriétés du système et les drapeaux de ligne de commande (comme jinfo) et d'obtenir des statistiques sur la collecte des déchets (comme jstat). L'outil jcmd a été qualifié de "couteau suisse pour étudier et résoudre les problèmes de votre application JVM" et de "joyau caché".

Voici la procédure à suivre pour invoquer la fonction jcmd :

  1. Aller à jcmd <pid> GC.heap_dump <file-path>
  2. Dans laquelle
  3. pid : est un identifiant de processus Java, pour lequel le vidage du tas sera capturé. De plus, l'option
  4. file-path : est un chemin de fichier dans lequel le vidage du tas sera imprimé.

Consultez-le pour obtenir plus d'informations sur la façon de prendre vidage du tas de Java .

1voto

Jim T Points 81

Afin d'effectuer un thread dump/heap dump à partir d'un processus Java enfant sous Windows, vous devez d'abord identifier le processus enfant.

En lançant la commande : jps vous pourrez obtenir tous les ID des processus java qui sont en cours d'exécution sur votre machine Windows. Dans cette liste, vous devez sélectionner l'Id du processus enfant. Une fois que vous avez l'ID du processus enfant, il existe plusieurs options pour capturer le vidage du fil et le vidage du tas.

Capturer les Thread Dumps :

Il existe 8 options pour capturer les vidages de threads :

  1. jstack
  2. tuer -3
  3. jvisualVM
  4. JMC
  5. Windows (Ctrl + Pause)
  6. ThreadMXBean
  7. Outils APM
  8. jcmd

Vous trouverez des détails sur chaque option dans cet article . Une fois que vous avez des vidages de threads de capture, vous pouvez utiliser des outils tels que fastThread , Samuraito analyser les vidages de fils.

Capturing Heap Dumps :

Il existe 7 options pour capturer les vidanges de tas :

  1. jmap

  2. -XX:+HeapDumpOnOutOfMemoryError

  3. jcmd

  4. JVisualVM

  5. JMX

  6. Approche programmatique

  7. Consoles administratives

Vous trouverez des détails sur chaque option dans cet article . Une fois que vous avez capturé le vidage du tas, vous pouvez utiliser des outils tels que Outil d'analyse de la mémoire d'Eclipse , HeapHero pour analyser les vidages de tas capturés.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X