alvinalexander.com | career | drupal | java | mac | mysql | perl | scala | uml | unix  

Java example source code file (JavaObject.java)

This example Java source code file (JavaObject.java) is included in the alvinalexander.com "Java Source Code Warehouse" project. The intent of this project is to help you "Learn Java by Example" TM.

Learn more about this Java project at its project page.

Java - Java tags/keywords

ioexception, javaboolean, javaclass, javadouble, javafield, javaobject, javaobjectref, javathing, number, readbuffer, runtimeexception, snapshot, string

The JavaObject.java Java example source code

/*
 * Copyright (c) 1997, 2008, Oracle and/or its affiliates. All rights reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.  Oracle designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Oracle in the LICENSE file that accompanied this code.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit www.oracle.com if you need additional information or have any
 * questions.
 */


/*
 * The Original Code is HAT. The Initial Developer of the
 * Original Code is Bill Foote, with contributions from others
 * at JavaSoft/Sun.
 */

package com.sun.tools.hat.internal.model;

import java.io.IOException;
import com.sun.tools.hat.internal.parser.ReadBuffer;

/**
 * Represents Java instance
 *
 * @author      Bill Foote
 */
public class JavaObject extends JavaLazyReadObject {

    private Object clazz;       // Number before resolve
                                // JavaClass after resolve
    /**
     * Construct a new JavaObject.
     *
     * @param classID id of the class object
     * @param offset The offset of field data
     */
    public JavaObject(long classID, long offset) {
        super(offset);
        this.clazz = makeId(classID);
    }

    public void resolve(Snapshot snapshot) {
        if (clazz instanceof JavaClass) {
            return;
        }
        if (clazz instanceof Number) {
            long classID = getIdValue((Number)clazz);
            clazz = snapshot.findThing(classID);
            if (! (clazz instanceof JavaClass)) {
                warn("Class " + Long.toHexString(classID) + " not found, " +
                     "adding fake class!");
                int length;
                ReadBuffer buf = snapshot.getReadBuffer();
                int idSize = snapshot.getIdentifierSize();
                long lenOffset = getOffset() + 2*idSize + 4;
                try {
                    length = buf.getInt(lenOffset);
                } catch (IOException exp) {
                    throw new RuntimeException(exp);
                }
                clazz = snapshot.addFakeInstanceClass(classID, length);
            }
        } else {
            throw new InternalError("should not reach here");
        }

        JavaClass cl = (JavaClass) clazz;
        cl.resolve(snapshot);

        // while resolving, parse fields in verbose mode.
        // but, getFields calls parseFields in non-verbose mode
        // to avoid printing warnings repeatedly.
        parseFields(getValue(), true);

        cl.addInstance(this);
        super.resolve(snapshot);
    }

    /**
     * Are we the same type as other?  We are iff our clazz is the
     * same type as other's.
     */
    public boolean isSameTypeAs(JavaThing other) {
        if (!(other instanceof JavaObject)) {
            return false;
        }
        JavaObject oo = (JavaObject) other;
        return getClazz().equals(oo.getClazz());
    }

    /**
     * Return our JavaClass object.  This may only be called after resolve.
     */
    public JavaClass getClazz() {
        return (JavaClass) clazz;
    }

    public JavaThing[] getFields() {
        // pass false to verbose mode so that dereference
        // warnings are not printed.
        return parseFields(getValue(), false);
    }

    // returns the value of field of given name
    public JavaThing getField(String name) {
        JavaThing[] flds = getFields();
        JavaField[] instFields = getClazz().getFieldsForInstance();
        for (int i = 0; i < instFields.length; i++) {
            if (instFields[i].getName().equals(name)) {
                return flds[i];
            }
        }
        return null;
    }

    public int compareTo(JavaThing other) {
        if (other instanceof JavaObject) {
            JavaObject oo = (JavaObject) other;
            return getClazz().getName().compareTo(oo.getClazz().getName());
        }
        return super.compareTo(other);
    }

    public void visitReferencedObjects(JavaHeapObjectVisitor v) {
        super.visitReferencedObjects(v);
        JavaThing[] flds = getFields();
        for (int i = 0; i < flds.length; i++) {
            if (flds[i] != null) {
                if (v.mightExclude()
                    && v.exclude(getClazz().getClassForField(i),
                                 getClazz().getFieldForInstance(i)))
                {
                    // skip it
                } else if (flds[i] instanceof JavaHeapObject) {
                    v.visit((JavaHeapObject) flds[i]);
                }
            }
        }
    }

    public boolean refersOnlyWeaklyTo(Snapshot ss, JavaThing other) {
        if (ss.getWeakReferenceClass() != null) {
            final int referentFieldIndex = ss.getReferentFieldIndex();
            if (ss.getWeakReferenceClass().isAssignableFrom(getClazz())) {
                //
                // REMIND:  This introduces a dependency on the JDK
                //      implementation that is undesirable.
                JavaThing[] flds = getFields();
                for (int i = 0; i < flds.length; i++) {
                    if (i != referentFieldIndex && flds[i] == other) {
                        return false;
                    }
                }
                return true;
            }
        }
        return false;
    }

    /**
     * Describe the reference that this thing has to target.  This will only
     * be called if target is in the array returned by getChildrenForRootset.
     */
    public String describeReferenceTo(JavaThing target, Snapshot ss) {
        JavaThing[] flds = getFields();
        for (int i = 0; i < flds.length; i++) {
            if (flds[i] == target) {
                JavaField f = getClazz().getFieldForInstance(i);
                return "field " + f.getName();
            }
        }
        return super.describeReferenceTo(target, ss);
    }

    public String toString() {
        if (getClazz().isString()) {
            JavaThing value = getField("value");
            if (value instanceof JavaValueArray) {
                return ((JavaValueArray)value).valueString();
            } else {
                return "null";
            }
        } else {
            return super.toString();
        }
    }

    // Internals only below this point

    /*
     * Java instance record (HPROF_GC_INSTANCE_DUMP) looks as below:
     *
     *     object ID
     *     stack trace serial number (int)
     *     class ID
     *     data length (int)
     *     byte[length]
     */
    protected final int readValueLength() throws IOException {
        JavaClass cl = getClazz();
        int idSize = cl.getIdentifierSize();
        long lengthOffset = getOffset() + 2*idSize + 4;
        return cl.getReadBuffer().getInt(lengthOffset);
    }

    protected final byte[] readValue() throws IOException {
        JavaClass cl = getClazz();
        int idSize = cl.getIdentifierSize();
        ReadBuffer buf = cl.getReadBuffer();
        long offset = getOffset() + 2*idSize + 4;
        int length = buf.getInt(offset);
        if (length == 0) {
            return Snapshot.EMPTY_BYTE_ARRAY;
        } else {
            byte[] res = new byte[length];
            buf.get(offset + 4, res);
            return res;
        }
    }

    private JavaThing[] parseFields(byte[] data, boolean verbose) {
        JavaClass cl = getClazz();
        int target = cl.getNumFieldsForInstance();
        JavaField[] fields = cl.getFields();
        JavaThing[] fieldValues = new JavaThing[target];
        Snapshot snapshot = cl.getSnapshot();
        int idSize = snapshot.getIdentifierSize();
        int fieldNo = 0;
        // In the dump file, the fields are stored in this order:
        // fields of most derived class (immediate class) are stored
        // first and then the super class and so on. In this object,
        // fields are stored in the reverse ("natural") order. i.e.,
        // fields of most super class are stored first.

        // target variable is used to compensate for the fact that
        // the dump file starts field values from the leaf working
        // upwards in the inheritance hierarchy, whereas JavaObject
        // starts with the top of the inheritance hierarchy and works down.
        target -= fields.length;
        JavaClass currClass = cl;
        int index = 0;
        for (int i = 0; i < fieldValues.length; i++, fieldNo++) {
            while (fieldNo >= fields.length) {
                currClass = currClass.getSuperclass();
                fields = currClass.getFields();
                fieldNo = 0;
                target -= fields.length;
            }
            JavaField f = fields[fieldNo];
            char sig = f.getSignature().charAt(0);
            switch (sig) {
                case 'L':
                case '[': {
                    long id = objectIdAt(index, data);
                    index += idSize;
                    JavaObjectRef ref = new JavaObjectRef(id);
                    fieldValues[target+fieldNo] = ref.dereference(snapshot, f, verbose);
                    break;
                }
                case 'Z': {
                    byte value = byteAt(index, data);
                    index++;
                    fieldValues[target+fieldNo] = new JavaBoolean(value != 0);
                    break;
                }
                case 'B': {
                    byte value = byteAt(index, data);
                    index++;
                    fieldValues[target+fieldNo] = new JavaByte(value);
                    break;
                }
                case 'S': {
                    short value = shortAt(index, data);
                    index += 2;
                    fieldValues[target+fieldNo] = new JavaShort(value);
                    break;
                }
                case 'C': {
                    char value = charAt(index, data);
                    index += 2;
                    fieldValues[target+fieldNo] = new JavaChar(value);
                    break;
                }
                case 'I': {
                    int value = intAt(index, data);
                    index += 4;
                    fieldValues[target+fieldNo] = new JavaInt(value);
                    break;
                }
                case 'J': {
                    long value = longAt(index, data);
                    index += 8;
                    fieldValues[target+fieldNo] = new JavaLong(value);
                    break;
                }
                case 'F': {
                    float value = floatAt(index, data);
                    index += 4;
                    fieldValues[target+fieldNo] = new JavaFloat(value);
                    break;
                }
                case 'D': {
                    double value = doubleAt(index, data);
                    index += 8;
                    fieldValues[target+fieldNo] = new JavaDouble(value);
                    break;
                }
                default:
                    throw new RuntimeException("invalid signature: " + sig);
            }
        }
        return fieldValues;
    }

    private void warn(String msg) {
        System.out.println("WARNING: " + msg);
    }
}

Other Java examples (source code examples)

Here is a short list of links related to this Java JavaObject.java source code file:

... this post is sponsored by my books ...

#1 New Release!

FP Best Seller

 

new blog posts

 

Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.

A percentage of advertising revenue from
pages under the /java/jwarehouse URI on this website is
paid back to open source projects.