Search in sources :

Example 1 with JavaMethod

use of com.ibm.dtfj.java.JavaMethod in project openj9 by eclipse.

the class PHDJavaRuntime method findLoaders.

/**
 * Helper method to try to allocate classes to the correct class loader
 * There isn't an explicit mention of the loader, but an outbound reference might be to the loader.
 * First find all the objects which are class loaders.
 * The look at each file, see if it has a reference to a loader object and if so allocate it to
 * that loader.
 * @param file
 * @throws IOException
 */
private void findLoaders(HeapdumpReader newreader) throws IOException {
    // Where all the classes orginally have been put
    final PHDJavaClassLoader boot = loaders.get(null);
    // Might fail to find a class with a very corrupt dump
    final JavaClass jlc = findClass("java/lang/Class");
    final long jlcAddress = jlc == null || jlc.getID() == null ? 0 : jlc.getID().getAddress();
    // Find all the class loader classes
    final JavaClass jcl = findClass("java/lang/ClassLoader");
    final HashMap<Long, JavaClass> classLoaderClasses = new HashMap<Long, JavaClass>();
    for (Iterator<JavaClass> it = boot.getDefinedClasses(); it.hasNext(); ) {
        JavaClass cls = it.next();
        if (cls instanceof CorruptData)
            continue;
        try {
            // Avoid bug with superclass loops by remembering superclasses
            // PHD Version 4 bug - bad superclass: J2RE 5.0 IBM J9 2.3 AIX ppc64-64 build 20080314_17962_BHdSMr
            HashSet<JavaClass> supers = new HashSet<JavaClass>();
            for (JavaClass j1 = cls; j1 != null && supers.add(j1); j1 = j1.getSuperclass()) {
                /* 
					 * See if either a superclass is java.lang.ClassLoader
					 * or if no superclass information is available (old Java 5)
					 * whether the name ends with "ClassLoader"
					 */
                if (j1.equals(jcl) || cls.getSuperclass() == null && !j1.isArray() && j1.getName().endsWith("ClassLoader")) {
                    ImagePointer ip = cls.getID();
                    if (ip != null) {
                        classLoaderClasses.put(ip.getAddress(), cls);
                    }
                }
            }
        } catch (CorruptDataException e) {
        // Ignore
        }
    }
    // Number of class objects not found at class addresses
    final int[] onHeapClasses = new int[1];
    // Find all the objects which are class loaders
    final PHDJavaHeap heap = heaps.get(0);
    final HashMap<Long, JavaObject> classObjects = new HashMap<Long, JavaObject>();
    // HeapdumpReader newreader = new HeapdumpReader(file, parentImage);
    final int adjustLen = newreader.version() == 4 && newreader.isJ9() ? 1 : 0;
    try {
        newreader.parse(new PortableHeapDumpListener() {

            public void classDump(long address, long superAddress, String name, int size, int flags, int hashCode, LongEnumeration refs) throws Exception {
            }

            public void objectArrayDump(long address, long classAddress, int flags, int hashCode, LongEnumeration refs, int length, long instanceSize) throws Exception {
                if (extraObjectsCache.containsKey(address)) {
                    // Don't bother saving reference information - we can get it later
                    JavaObject jo = new PHDJavaObject.Builder(heap, address, arrayOf(classAddress, refs, adjustLen), flags, hashCode).length(length - adjustLen).instanceSize(instanceSize).build();
                    extraObjectsCache.put(address, jo);
                }
            }

            public void objectDump(long address, long classAddress, int flags, int hashCode, LongEnumeration refs, long instanceSize) throws Exception {
                JavaClass cls = classLoaderClasses.get(classAddress);
                JavaObject jo;
                if (cls != null) {
                    // Object of type java.lang.ClassLoader, so create the object and the class loader
                    jo = new PHDJavaObject.Builder(heap, address, cls, flags, hashCode).refs(refs, 0).length(PHDJavaObject.SIMPLE_OBJECT).instanceSize(instanceSize).build();
                    PHDJavaClassLoader load = new PHDJavaClassLoader(jo);
                    loaders.put(jo, load);
                } else if (classAddress == jlcAddress) {
                    if (boot.findClass(address) == null) {
                        ++onHeapClasses[0];
                    }
                    jo = new PHDJavaObject.Builder(heap, address, jlc, flags, hashCode).refs(refs, 0).length(PHDJavaObject.SIMPLE_OBJECT).instanceSize(instanceSize).build();
                    classObjects.put(address, jo);
                } else {
                    jo = null;
                }
                if (extraObjectsCache.containsKey(address)) {
                    if (jo == null) {
                        jo = new PHDJavaObject.Builder(heap, address, findClass(classAddress), flags, hashCode).refs(refs, 0).length(PHDJavaObject.SIMPLE_OBJECT).build();
                    }
                    extraObjectsCache.put(address, jo);
                }
            }

            public void primitiveArrayDump(long address, int type, int length, int flags, int hashCode, long instanceSize) throws Exception {
                if (extraObjectsCache.containsKey(address)) {
                    // Create a full object as we have the data
                    JavaObject jo = new PHDJavaObject.Builder(heap, address, findArrayOfType(type), flags, hashCode).refsAsArray(NOREFS, 0).length(length).instanceSize(instanceSize).build();
                    extraObjectsCache.put(address, jo);
                }
            }
        });
    } catch (Exception e) {
    // Ignore the exception - we will have seen it elsewhere
    // e.printStackTrace();
    } finally {
        newreader.close();
        newreader = null;
    }
    // Assign classes to the correct loaders
    // Also try to set up on/off-heap class addresses
    PHDJavaClassLoader boot2 = null;
    int foundLoader = 0;
    int notFoundLoader = 0;
    // How many java/lang classes the possible boot loader has loaded
    int loaderJavaLangCount = 0;
    boolean useFirstObjectRefAsLoader = onHeapClasses[0] == 0;
    for (Iterator<JavaClass> it = boot.getDefinedClasses(); it.hasNext(); ) {
        JavaClass j1 = it.next();
        PHDJavaClassLoader bestLoader = null;
        for (Iterator<JavaReference> it2 = j1.getReferences(); it2.hasNext(); ) {
            JavaReference jr = it2.next();
            try {
                // Is the first outbound object reference to a class loader?
                if (jr.isObjectReference()) {
                    JavaObject jo = (JavaObject) jr.getTarget();
                    PHDJavaClassLoader newLoader = loaders.get(jo);
                    if (newLoader != null) {
                        if (bestLoader == null || !useFirstObjectRefAsLoader) {
                            bestLoader = newLoader;
                        }
                    } else if (onHeapClasses[0] > 0) {
                        long addr = jo.getID().getAddress();
                        JavaObject jo2 = classObjects.get(addr);
                        if (jo2 != null) {
                            // For Java 6 jdmpview PHD files the on-heap class object is the last ref
                            // retrieve the full JavaObject from walking the heap earlier
                            ((PHDJavaClass) j1).setJavaObject(jo2);
                        }
                    }
                    // unless using off-heap classes when it is the last reference.
                    if (!j1.isArray() && useFirstObjectRefAsLoader && onHeapClasses[0] == 0)
                        break;
                }
            } catch (CorruptDataException e) {
            // e.printStackTrace();
            } catch (DataUnavailable e) {
            // e.printStackTrace();
            }
        }
        if (bestLoader != null) {
            ++foundLoader;
            // Don't remove the classes from the original loader, nor change the loader
            // as otherwise finding the array type fails
            bestLoader.prepareToMove(boot, j1);
            // Is the class by any chance the type of the class loader?
            try {
                if (boot2 == null && (j1.equals(jlc) || j1.equals(bestLoader.getObject().getJavaClass()))) {
                    // We have found the new bootstrap class loader
                    // Beware java 1.4.2 com/ibm/rmi/util/ClassInfo$NULL_CL_CLASS passes this test!
                    boot2 = bestLoader;
                }
                if (boot2 == bestLoader && j1.getName().startsWith("java/lang/"))
                    ++loaderJavaLangCount;
            } catch (CorruptDataException e) {
            }
        } else {
            ++notFoundLoader;
        }
        // Try retrieving the full JavaObject for the JavaClass
        try {
            JavaObject jo = j1.getObject();
            if (jo != null) {
                long addr = jo.getID().getAddress();
                JavaObject jo2 = classObjects.get(addr);
                if (jo2 != null) {
                    ((PHDJavaClass) j1).setJavaObject(jo2);
                }
            }
        } catch (CorruptDataException e) {
        }
    }
    // Ignore a bootstrap loader which hasn't loaded 5 java/lang classes
    if (loaderJavaLangCount < 5)
        boot2 = null;
    // Haven't found any loaders, but have a javacore file with loader information
    if (metaJavaRuntime != null) {
        for (Iterator i = metaJavaRuntime.getJavaClassLoaders(); i.hasNext(); ) {
            Object next = i.next();
            if (next instanceof CorruptData)
                continue;
            JavaClassLoader jcl2 = (JavaClassLoader) next;
            try {
                JavaObject lo = jcl2.getObject();
                if (lo != null) {
                    ImagePointer addr = lo.getID();
                    if (addr != null) {
                        ImagePointer ip = space.getPointer(addr.getAddress());
                        JavaObject jo = getObjectAtAddress(ip);
                        PHDJavaClassLoader newLoader = loaders.get(jo);
                        JavaClass loaderClass;
                        if (newLoader == null) {
                            try {
                                // Should be safe to find the class of 'jo' without rereading the PHD file
                                // as at least a dummy object should be in the extra objects cache.
                                // It could be that the object is still a dummy one with no proper class.
                                loaderClass = jo.getJavaClass();
                            } catch (CorruptDataException e) {
                                loaderClass = null;
                            }
                            JavaClass javacoreLoaderClass;
                            try {
                                javacoreLoaderClass = lo.getJavaClass();
                            } catch (CorruptDataException e) {
                                javacoreLoaderClass = null;
                            }
                            // Mismatch occurs with J2RE 5.0 IBM J9 2.3 Linux amd64-64 build j9vmxa6423-20091104
                            if (loaderClass != null && javacoreLoaderClass != null && (loaderClass.isArray() || loaderClass.getID() != null && javacoreLoaderClass.getID() != null && loaderClass.getID().getAddress() != javacoreLoaderClass.getID().getAddress())) {
                            // System.out.println("Skipping loader "+newLoader+" "+jo+" "+jo.getJavaClass()+" "+lo+" "+lo.getJavaClass()+" "+Long.toHexString(addr.getAddress())+" "+ip);
                            } else {
                                // The object should have been listed in the extra objects, so may now be the proper object
                                newLoader = new PHDJavaClassLoader(jo);
                                loaders.put(jo, newLoader);
                            }
                        } else {
                            // Replace with the offical object
                            jo = newLoader.getObject();
                            loaderClass = jo.getJavaClass();
                        }
                        if (newLoader != null) {
                            for (Iterator i2 = jcl2.getDefinedClasses(); i2.hasNext(); ) {
                                Object next2 = i2.next();
                                if (next2 instanceof CorruptData)
                                    continue;
                                JavaClass jc2 = (JavaClass) next2;
                                ImagePointer ip2 = jc2.getID();
                                JavaClass j1;
                                if (ip2 != null) {
                                    long claddr = ip2.getAddress();
                                    j1 = boot.findClass(claddr);
                                    // Not found by address, so try by name.
                                    if (j1 == null) {
                                        // But only if it is the only class of that name
                                        j1 = boot.findClassUnique(jc2.getName());
                                    } else {
                                        // Found by address
                                        try {
                                            j1.getName();
                                        } catch (CorruptDataException e) {
                                            // Our class doesn't have a name, so perhaps the javacore has the name
                                            try {
                                                String actualName = jc2.getName();
                                                PHDJavaClass pj1 = (PHDJavaClass) j1;
                                                // We will need to reindex the classloader as the name as changed
                                                pj1.setName(actualName);
                                            } catch (CorruptDataException e2) {
                                            }
                                        }
                                    }
                                } else {
                                    // But only if it is the only class of that name
                                    j1 = boot.findClassUnique(jc2.getName());
                                }
                                if (j1 != null) {
                                    newLoader.prepareToMove(boot, j1);
                                    // listed in javacore causes problems as byte etc. aren't listed
                                    if (j1.equals(loaderClass) || j1.equals(jlc)) {
                                        // We have found the new bootstrap class loader
                                        boot2 = newLoader;
                                    }
                                    for (Iterator i3 = jc2.getDeclaredMethods(); i3.hasNext(); ) {
                                        Object next3 = i3.next();
                                        if (next3 instanceof CorruptData)
                                            continue;
                                        JavaMethod jm = (JavaMethod) next3;
                                        PHDJavaClass pj1 = (PHDJavaClass) j1;
                                        pj1.addMethod(new PHDJavaMethod(space, pj1, jm));
                                    }
                                }
                            }
                        }
                    }
                }
            } catch (CorruptDataException e) {
            } catch (DataUnavailable e) {
            } catch (MemoryAccessException e) {
            }
        }
    }
    // Move the classes to the correct class loaders
    for (Iterator<JavaClass> it = boot.getDefinedClasses(); it.hasNext(); ) {
        JavaClass j1 = it.next();
        try {
            JavaClassLoader jcl2 = j1.getClassLoader();
            if (!boot.equals(jcl2) && jcl2 instanceof PHDJavaClassLoader) {
                transferClass(boot, (PHDJavaClassLoader) jcl2, j1);
            }
        } catch (CorruptDataException e) {
        }
    }
    // Reindex the loaders to account for the removed classes
    for (PHDJavaClassLoader loader : loaders.values()) {
        loader.initCache();
    }
    if (boot2 != null) {
        // Move remaining classes to new boot loader
        for (Iterator<JavaClass> it = boot.getDefinedClasses(); it.hasNext(); ) {
            JavaClass j1 = it.next();
            boot2.prepareToMove(boot, j1);
            transferClass(boot, boot2, j1);
        }
        // index the new boot loader to account for the added files
        boot2.initCache();
        // Remove the original boot class loader as it has no classes
        loaders.remove(null);
    } else {
        // There may be duplicate array classes in the boot loader
        for (Iterator<JavaClass> it = boot.getDefinedClasses(); it.hasNext(); ) {
            JavaClass j1 = it.next();
            JavaClass j2 = boot.setArrayType(this, boot, j1);
        }
        // index the boot loader to account for the added files
        boot.initCache();
    }
}
Also used : PortableHeapDumpListener(com.ibm.dtfj.phd.parser.PortableHeapDumpListener) HashMap(java.util.HashMap) LinkedHashMap(java.util.LinkedHashMap) CorruptDataException(com.ibm.dtfj.image.CorruptDataException) ImagePointer(com.ibm.dtfj.image.ImagePointer) JavaReference(com.ibm.dtfj.java.JavaReference) LongEnumeration(com.ibm.dtfj.phd.util.LongEnumeration) Iterator(java.util.Iterator) DataUnavailable(com.ibm.dtfj.image.DataUnavailable) JavaMethod(com.ibm.dtfj.java.JavaMethod) MemoryAccessException(com.ibm.dtfj.image.MemoryAccessException) HashSet(java.util.HashSet) MemoryAccessException(com.ibm.dtfj.image.MemoryAccessException) IOException(java.io.IOException) CorruptDataException(com.ibm.dtfj.image.CorruptDataException) JavaClass(com.ibm.dtfj.java.JavaClass) JavaObject(com.ibm.dtfj.java.JavaObject) JavaClassLoader(com.ibm.dtfj.java.JavaClassLoader) CorruptData(com.ibm.dtfj.image.CorruptData) JavaObject(com.ibm.dtfj.java.JavaObject)

Example 2 with JavaMethod

use of com.ibm.dtfj.java.JavaMethod in project openj9 by eclipse.

the class JavaMethodComparator method testEquals.

// getByteCodeSections()
// getCompiledSections()
public void testEquals(Object ddrObject, Object jextractObject, int members) {
    JavaMethod ddrJavaMethod = (JavaMethod) ddrObject;
    JavaMethod jextractJavaMethod = (JavaMethod) jextractObject;
    ImageSectionComparator imageSectionComparator = new ImageSectionComparator();
    // getByteCodeSections()
    if ((BYTE_CODE_SECTIONS & members) != 0)
        imageSectionComparator.testComparatorIteratorEquals(ddrJavaMethod, jextractJavaMethod, "getBytecodeSections", ImageSection.class);
    // getCompiledSections()
    if ((COMPILED_SECTIONS & members) != 0) {
        compareCompiledSections(ddrJavaMethod, jextractJavaMethod, imageSectionComparator);
    }
    // getName()
    if ((NAME & members) != 0)
        testJavaEquals(ddrJavaMethod, jextractJavaMethod, "getName");
}
Also used : JavaMethod(com.ibm.dtfj.java.JavaMethod) ImageSection(com.ibm.dtfj.image.ImageSection)

Example 3 with JavaMethod

use of com.ibm.dtfj.java.JavaMethod in project openj9 by eclipse.

the class JavaMethodTest method getCompiledSectionsTest.

@Test
public void getCompiledSectionsTest() {
    for (int i = 0; i < ddrTestObjects.size(); i++) {
        JavaMethod ddrJavaMethod = (JavaMethod) ddrTestObjects.get(i);
        JavaMethod jextractJavaMethod = (JavaMethod) jextractTestObjects.get(i);
        JavaMethodComparator.compareCompiledSections(ddrJavaMethod, jextractJavaMethod, imageSectionComparator);
    }
}
Also used : JavaMethod(com.ibm.dtfj.java.JavaMethod) Test(org.junit.Test)

Example 4 with JavaMethod

use of com.ibm.dtfj.java.JavaMethod in project openj9 by eclipse.

the class PHDJavaLocation method toString.

/*
	 * Get a description of the frame in the same format as a stack trace 
	 */
public String toString() {
    StringBuilder sb = new StringBuilder();
    try {
        JavaMethod m = getMethod();
        sb.append(m.getDeclaringClass().getName().replace('/', '.'));
        sb.append('.');
        sb.append(m.getName());
    } catch (CorruptDataException e) {
        sb.append("corrupt");
    } catch (DataUnavailable e) {
        sb.append("data unavailable");
    }
    sb.append('(');
    boolean d = false;
    try {
        sb.append(getFilename());
        d = true;
        int line = getLineNumber();
        sb.append(':');
        sb.append(line);
    } catch (CorruptDataException e) {
        try {
            if (getCompilationLevel() > 0) {
                if (d)
                    sb.append('(');
                sb.append("Compiled Code");
                if (d)
                    sb.append(')');
            }
        } catch (CorruptDataException e2) {
        }
    } catch (DataUnavailable e) {
        try {
            if (getCompilationLevel() > 0) {
                if (d)
                    sb.append('(');
                sb.append("Compiled Code");
                if (d)
                    sb.append(')');
            }
        } catch (CorruptDataException e2) {
        }
    } finally {
        sb.append(')');
    }
    return sb.toString();
}
Also used : JavaMethod(com.ibm.dtfj.java.JavaMethod) DataUnavailable(com.ibm.dtfj.image.DataUnavailable) CorruptDataException(com.ibm.dtfj.image.CorruptDataException)

Example 5 with JavaMethod

use of com.ibm.dtfj.java.JavaMethod in project openj9 by eclipse.

the class ClassOutput method printMethods.

public static void printMethods(Iterator methods, PrintStream out) {
    while (methods.hasNext()) {
        JavaMethod jMethod = (JavaMethod) methods.next();
        try {
            out.print("Bytecode range(s): ");
            Iterator imageSections = jMethod.getBytecodeSections();
            boolean firstSectionPassed = false;
            while (imageSections.hasNext()) {
                ImageSection is = (ImageSection) imageSections.next();
                long baseAddress = is.getBaseAddress().getAddress();
                long endAddress = baseAddress + is.getSize();
                if (firstSectionPassed) {
                    out.print(", ");
                }
                out.print(Long.toHexString(baseAddress) + " -- " + Long.toHexString(endAddress));
                firstSectionPassed = true;
            }
            out.print(":  ");
            String signature;
            try {
                out.print(Utils.getMethodModifierString(jMethod));
            } catch (CorruptDataException e) {
                out.print(Exceptions.getCorruptDataExceptionString());
            }
            try {
                signature = jMethod.getSignature();
            } catch (CorruptDataException e) {
                out.print(Exceptions.getCorruptDataExceptionString());
                signature = null;
            }
            if (null != signature) {
                String name = Utils.getReturnValueName(signature);
                if (null == name) {
                    out.print("<unknown>");
                } else {
                    out.print(name);
                }
            }
            out.print(" ");
            out.print(jMethod.getName());
            if (null != signature) {
                String name = Utils.getMethodSignatureName(signature);
                if (null == name) {
                    out.print("<unknown>");
                } else {
                    out.print(name);
                }
            }
            out.print("\n");
        } catch (CorruptDataException cde) {
            out.print("N/A (CorruptDataException occurred)");
        }
    }
}
Also used : Iterator(java.util.Iterator) JavaMethod(com.ibm.dtfj.java.JavaMethod) ImageSection(com.ibm.dtfj.image.ImageSection) CorruptDataException(com.ibm.dtfj.image.CorruptDataException)

Aggregations

JavaMethod (com.ibm.dtfj.java.JavaMethod)8 CorruptDataException (com.ibm.dtfj.image.CorruptDataException)6 ImageSection (com.ibm.dtfj.image.ImageSection)4 Iterator (java.util.Iterator)4 DataUnavailable (com.ibm.dtfj.image.DataUnavailable)3 JavaClass (com.ibm.dtfj.java.JavaClass)3 JavaClassLoader (com.ibm.dtfj.java.JavaClassLoader)2 JavaObject (com.ibm.dtfj.java.JavaObject)2 CorruptData (com.ibm.dtfj.image.CorruptData)1 ImagePointer (com.ibm.dtfj.image.ImagePointer)1 MemoryAccessException (com.ibm.dtfj.image.MemoryAccessException)1 JavaReference (com.ibm.dtfj.java.JavaReference)1 JavaRuntime (com.ibm.dtfj.java.JavaRuntime)1 PortableHeapDumpListener (com.ibm.dtfj.phd.parser.PortableHeapDumpListener)1 LongEnumeration (com.ibm.dtfj.phd.util.LongEnumeration)1 IOException (java.io.IOException)1 HashMap (java.util.HashMap)1 HashSet (java.util.HashSet)1 LinkedHashMap (java.util.LinkedHashMap)1 Test (org.junit.Test)1