FileDocCategorySizeDatePackage
ClassDefItem.javaAPI DocAndroid 5.1 API13832Thu Mar 12 22:18:30 GMT 2015com.android.dx.dex.file

ClassDefItem

public final class ClassDefItem extends IndexedItem
Representation of a Dalvik class, which is basically a set of members (fields or methods) along with a few more pieces of information.

Fields Summary
private final com.android.dx.rop.cst.CstType
thisClass
{@code non-null;} type constant for this class
private final int
accessFlags
access flags
private final com.android.dx.rop.cst.CstType
superclass
{@code null-ok;} superclass or {@code null} if this class is a/the root class
private TypeListItem
interfaces
{@code null-ok;} list of implemented interfaces
private final com.android.dx.rop.cst.CstString
sourceFile
{@code null-ok;} source file name or {@code null} if unknown
private final ClassDataItem
classData
{@code non-null;} associated class data object
private EncodedArrayItem
staticValuesItem
{@code null-ok;} item wrapper for the static values, initialized in {@link #addContents}
private AnnotationsDirectoryItem
annotationsDirectory
{@code non-null;} annotations directory
Constructors Summary
public ClassDefItem(com.android.dx.rop.cst.CstType thisClass, int accessFlags, com.android.dx.rop.cst.CstType superclass, com.android.dx.rop.type.TypeList interfaces, com.android.dx.rop.cst.CstString sourceFile)
Constructs an instance. Its sets of members and annotations are initially empty.

param
thisClass {@code non-null;} type constant for this class
param
accessFlags access flags
param
superclass {@code null-ok;} superclass or {@code null} if this class is a/the root class
param
interfaces {@code non-null;} list of implemented interfaces
param
sourceFile {@code null-ok;} source file name or {@code null} if unknown

        if (thisClass == null) {
            throw new NullPointerException("thisClass == null");
        }

        /*
         * TODO: Maybe check accessFlags and superclass, at
         * least for easily-checked stuff?
         */

        if (interfaces == null) {
            throw new NullPointerException("interfaces == null");
        }

        this.thisClass = thisClass;
        this.accessFlags = accessFlags;
        this.superclass = superclass;
        this.interfaces =
            (interfaces.size() == 0) ? null :  new TypeListItem(interfaces);
        this.sourceFile = sourceFile;
        this.classData = new ClassDataItem(thisClass);
        this.staticValuesItem = null;
        this.annotationsDirectory = new AnnotationsDirectoryItem();
    
Methods Summary
public voidaddContents(DexFile file)
{@inheritDoc}

        TypeIdsSection typeIds = file.getTypeIds();
        MixedItemSection byteData = file.getByteData();
        MixedItemSection wordData = file.getWordData();
        MixedItemSection typeLists = file.getTypeLists();
        StringIdsSection stringIds = file.getStringIds();

        typeIds.intern(thisClass);

        if (!classData.isEmpty()) {
            MixedItemSection classDataSection = file.getClassData();
            classDataSection.add(classData);

            CstArray staticValues = classData.getStaticValuesConstant();
            if (staticValues != null) {
                staticValuesItem =
                    byteData.intern(new EncodedArrayItem(staticValues));
            }
        }

        if (superclass != null) {
            typeIds.intern(superclass);
        }

        if (interfaces != null) {
            interfaces = typeLists.intern(interfaces);
        }

        if (sourceFile != null) {
            stringIds.intern(sourceFile);
        }

        if (! annotationsDirectory.isEmpty()) {
            if (annotationsDirectory.isInternable()) {
                annotationsDirectory = wordData.intern(annotationsDirectory);
            } else {
                wordData.add(annotationsDirectory);
            }
        }
    
public voidaddDirectMethod(EncodedMethod method)
Adds a direct ({@code static} and/or {@code private}) method.

param
method {@code non-null;} the method to add

        classData.addDirectMethod(method);
    
public voidaddFieldAnnotations(com.android.dx.rop.cst.CstFieldRef field, com.android.dx.rop.annotation.Annotations annotations, DexFile dexFile)
Adds a field annotations item to this class.

param
field {@code non-null;} field in question
param
annotations {@code non-null;} associated annotations to add
param
dexFile {@code non-null;} dex output

        annotationsDirectory.addFieldAnnotations(field, annotations, dexFile);
    
public voidaddInstanceField(EncodedField field)
Adds an instance field.

param
field {@code non-null;} the field to add

        classData.addInstanceField(field);
    
public voidaddMethodAnnotations(com.android.dx.rop.cst.CstMethodRef method, com.android.dx.rop.annotation.Annotations annotations, DexFile dexFile)
Adds a method annotations item to this class.

param
method {@code non-null;} method in question
param
annotations {@code non-null;} associated annotations to add
param
dexFile {@code non-null;} dex output

        annotationsDirectory.addMethodAnnotations(method, annotations, dexFile);
    
public voidaddParameterAnnotations(com.android.dx.rop.cst.CstMethodRef method, com.android.dx.rop.annotation.AnnotationsList list, DexFile dexFile)
Adds a parameter annotations item to this class.

param
method {@code non-null;} method in question
param
list {@code non-null;} associated list of annotation sets to add
param
dexFile {@code non-null;} dex output

        annotationsDirectory.addParameterAnnotations(method, list, dexFile);
    
public voidaddStaticField(EncodedField field, com.android.dx.rop.cst.Constant value)
Adds a static field.

param
field {@code non-null;} the field to add
param
value {@code null-ok;} initial value for the field, if any

        classData.addStaticField(field, value);
    
public voidaddVirtualMethod(EncodedMethod method)
Adds a virtual method.

param
method {@code non-null;} the method to add

        classData.addVirtualMethod(method);
    
public voiddebugPrint(java.io.Writer out, boolean verbose)
Prints out the contents of this instance, in a debugging-friendly way.

param
out {@code non-null;} where to output to
param
verbose whether to be verbose with the output

        PrintWriter pw = Writers.printWriterFor(out);

        pw.println(getClass().getName() + " {");
        pw.println("  accessFlags: " + Hex.u2(accessFlags));
        pw.println("  superclass: " + superclass);
        pw.println("  interfaces: " +
                ((interfaces == null) ? "<none>" : interfaces));
        pw.println("  sourceFile: " +
                ((sourceFile == null) ? "<none>" : sourceFile.toQuoted()));

        classData.debugPrint(out, verbose);
        annotationsDirectory.debugPrint(pw);

        pw.println("}");
    
public intgetAccessFlags()
Gets the access flags.

return
the access flags

        return accessFlags;
    
public com.android.dx.rop.type.TypeListgetInterfaces()
Gets the list of interfaces implemented.

return
{@code non-null;} the interfaces list

        if (interfaces == null) {
            return StdTypeList.EMPTY;
        }

        return interfaces.getList();
    
public com.android.dx.rop.annotation.AnnotationsgetMethodAnnotations(com.android.dx.rop.cst.CstMethodRef method)
Gets the method annotations for a given method, if any. This is meant for use by debugging / dumping code.

param
method {@code non-null;} the method
return
{@code null-ok;} the method annotations, if any

        return annotationsDirectory.getMethodAnnotations(method);
    
public java.util.ArrayListgetMethods()
Gets all the methods in this class. The returned list is not linked in any way to the underlying lists contained in this instance, but the objects contained in the list are shared.

return
{@code non-null;} list of all methods

        return classData.getMethods();
    
public com.android.dx.rop.annotation.AnnotationsListgetParameterAnnotations(com.android.dx.rop.cst.CstMethodRef method)
Gets the parameter annotations for a given method, if any. This is meant for use by debugging / dumping code.

param
method {@code non-null;} the method
return
{@code null-ok;} the parameter annotations, if any

        return annotationsDirectory.getParameterAnnotations(method);
    
public com.android.dx.rop.cst.CstStringgetSourceFile()
Gets the source file name.

return
{@code null-ok;} the source file name or {@code null} if unknown

        return sourceFile;
    
public com.android.dx.rop.cst.CstTypegetSuperclass()
Gets the superclass.

return
{@code null-ok;} the superclass or {@code null} if this class is a/the root class

        return superclass;
    
public com.android.dx.rop.cst.CstTypegetThisClass()
Gets the constant corresponding to this class.

return
{@code non-null;} the constant

        return thisClass;
    
public ItemTypeitemType()
{@inheritDoc}

        return ItemType.TYPE_CLASS_DEF_ITEM;
    
public voidsetClassAnnotations(com.android.dx.rop.annotation.Annotations annotations, DexFile dexFile)
Sets the direct annotations on this class. These are annotations made on the class, per se, as opposed to on one of its members. It is only valid to call this method at most once per instance.

param
annotations {@code non-null;} annotations to set for this class
param
dexFile {@code non-null;} dex output

        annotationsDirectory.setClassAnnotations(annotations, dexFile);
    
public intwriteSize()
{@inheritDoc}

        return SizeOf.CLASS_DEF_ITEM;
    
public voidwriteTo(DexFile file, com.android.dx.util.AnnotatedOutput out)
{@inheritDoc}

        boolean annotates = out.annotates();
        TypeIdsSection typeIds = file.getTypeIds();
        int classIdx = typeIds.indexOf(thisClass);
        int superIdx = (superclass == null) ? -1 :
            typeIds.indexOf(superclass);
        int interOff = OffsettedItem.getAbsoluteOffsetOr0(interfaces);
        int annoOff = annotationsDirectory.isEmpty() ? 0 :
            annotationsDirectory.getAbsoluteOffset();
        int sourceFileIdx = (sourceFile == null) ? -1 :
            file.getStringIds().indexOf(sourceFile);
        int dataOff = classData.isEmpty()? 0 : classData.getAbsoluteOffset();
        int staticValuesOff =
            OffsettedItem.getAbsoluteOffsetOr0(staticValuesItem);

        if (annotates) {
            out.annotate(0, indexString() + ' " + thisClass.toHuman());
            out.annotate(4, "  class_idx:           " + Hex.u4(classIdx));
            out.annotate(4, "  access_flags:        " +
                         AccessFlags.classString(accessFlags));
            out.annotate(4, "  superclass_idx:      " + Hex.u4(superIdx) +
                         " // " + ((superclass == null) ? "<none>" :
                          superclass.toHuman()));
            out.annotate(4, "  interfaces_off:      " + Hex.u4(interOff));
            if (interOff != 0) {
                TypeList list = interfaces.getList();
                int sz = list.size();
                for (int i = 0; i < sz; i++) {
                    out.annotate(0, "    " + list.getType(i).toHuman());
                }
            }
            out.annotate(4, "  source_file_idx:     " + Hex.u4(sourceFileIdx) +
                         " // " + ((sourceFile == null) ? "<none>" :
                          sourceFile.toHuman()));
            out.annotate(4, "  annotations_off:     " + Hex.u4(annoOff));
            out.annotate(4, "  class_data_off:      " + Hex.u4(dataOff));
            out.annotate(4, "  static_values_off:   " +
                    Hex.u4(staticValuesOff));
        }

        out.writeInt(classIdx);
        out.writeInt(accessFlags);
        out.writeInt(superIdx);
        out.writeInt(interOff);
        out.writeInt(sourceFileIdx);
        out.writeInt(annoOff);
        out.writeInt(dataOff);
        out.writeInt(staticValuesOff);