FileDocCategorySizeDatePackage
BasicBlock.javaAPI DocAndroid 5.1 API8676Thu Mar 12 22:18:30 GMT 2015com.android.dx.rop.code

BasicBlock

public final class BasicBlock extends Object implements com.android.dx.util.LabeledItem
Basic block of register-based instructions.

Fields Summary
private final int
label
{@code >= 0;} target label for this block
private final InsnList
insns
{@code non-null;} list of instructions in this block
private final com.android.dx.util.IntList
successors
{@code non-null;} full list of successors that this block may branch to
private final int
primarySuccessor
{@code >= -1;} the primary / standard-flow / "default" successor, or {@code -1} if this block has no successors (that is, it exits the function/method)
Constructors Summary
public BasicBlock(int label, InsnList insns, com.android.dx.util.IntList successors, int primarySuccessor)
Constructs an instance. The predecessor set is set to {@code null}.

param
label {@code >= 0;} target label for this block
param
insns {@code non-null;} list of instructions in this block
param
successors {@code non-null;} full list of successors that this block may branch to
param
primarySuccessor {@code >= -1;} the primary / standard-flow / "default" successor, or {@code -1} if this block has no successors (that is, it exits the function/method or is an unconditional throw)

        if (label < 0) {
            throw new IllegalArgumentException("label < 0");
        }

        try {
            insns.throwIfMutable();
        } catch (NullPointerException ex) {
            // Elucidate exception.
            throw new NullPointerException("insns == null");
        }

        int sz = insns.size();

        if (sz == 0) {
            throw new IllegalArgumentException("insns.size() == 0");
        }

        for (int i = sz - 2; i >= 0; i--) {
            Rop one = insns.get(i).getOpcode();
            if (one.getBranchingness() != Rop.BRANCH_NONE) {
                throw new IllegalArgumentException("insns[" + i + "] is a " +
                                                   "branch or can throw");
            }
        }

        Insn lastInsn = insns.get(sz - 1);
        if (lastInsn.getOpcode().getBranchingness() == Rop.BRANCH_NONE) {
            throw new IllegalArgumentException("insns does not end with " +
                                               "a branch or throwing " +
                                               "instruction");
        }

        try {
            successors.throwIfMutable();
        } catch (NullPointerException ex) {
            // Elucidate exception.
            throw new NullPointerException("successors == null");
        }

        if (primarySuccessor < -1) {
            throw new IllegalArgumentException("primarySuccessor < -1");
        }

        if (primarySuccessor >= 0 && !successors.contains(primarySuccessor)) {
            throw new IllegalArgumentException(
                    "primarySuccessor " + primarySuccessor + " not in successors " + successors);
        }

        this.label = label;
        this.insns = insns;
        this.successors = successors;
        this.primarySuccessor = primarySuccessor;
    
Methods Summary
public booleancanThrow()
Returns whether this block might throw an exception. This is just a convenient shorthand for {@code getLastInsn().canThrow()}.

return
{@code true} iff this block might throw an exception

        return insns.getLast().canThrow();
    
public booleanequals(java.lang.Object other)
{@inheritDoc} Instances of this class compare by identity. That is, {@code x.equals(y)} is only true if {@code x == y}.

        return (this == other);
    
public com.android.dx.rop.type.TypeListgetExceptionHandlerTypes()
Returns the exception handler types associated with this block, if any. This is just a shorthand for inspecting the last instruction in the block to see if it could throw, and if so, grabbing the catch list out of it. If not, this returns an empty list (not {@code null}).

return
{@code non-null;} the exception handler types associated with this block

        Insn lastInsn = insns.getLast();
        return lastInsn.getCatches();
    
public InsngetFirstInsn()
Gets the first instruction of this block. This is just a convenient shorthand for {@code getInsns().get(0)}.

return
{@code non-null;} the first instruction

        return insns.get(0);
    
public InsnListgetInsns()
Gets the list of instructions inside this block.

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

        return insns;
    
public intgetLabel()
Gets the target label of this block.

return
{@code >= 0;} the label

        return label;
    
public InsngetLastInsn()
Gets the last instruction of this block. This is just a convenient shorthand for {@code getInsns().getLast()}.

return
{@code non-null;} the last instruction

        return insns.getLast();
    
public intgetPrimarySuccessor()
Gets the primary successor of this block.

return
{@code >= -1;} the primary successor, or {@code -1} if this block has no successors at all

        return primarySuccessor;
    
public intgetSecondarySuccessor()
Gets the secondary successor of this block. It is only valid to call this method on blocks that have exactly two successors.

return
{@code >= 0;} the secondary successor

        if (successors.size() != 2) {
            throw new UnsupportedOperationException(
                    "block doesn't have exactly two successors");
        }

        int succ = successors.get(0);
        if (succ == primarySuccessor) {
            succ = successors.get(1);
        }

        return succ;
    
public com.android.dx.util.IntListgetSuccessors()
Gets the list of successors that this block may branch to.

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

        return successors;
    
public booleanhasExceptionHandlers()
Returns whether this block has any associated exception handlers. This is just a shorthand for inspecting the last instruction in the block to see if it could throw, and if so, whether it in fact has any associated handlers.

return
{@code true} iff this block has any associated exception handlers

        Insn lastInsn = insns.getLast();
        return lastInsn.getCatches().size() != 0;
    
public inthashCode()
{@inheritDoc} Return the identity hashcode of this instance. This is proper, since instances of this class compare by identity (see {@link #equals}).

        return System.identityHashCode(this);
    
public java.lang.StringtoString()

        return '{" + Hex.u2(label) + '}";
    
public com.android.dx.rop.code.BasicBlockwithRegisterOffset(int delta)
Returns an instance that is identical to this one, except that the registers in each instruction are offset by the given amount.

param
delta the amount to offset register numbers by
return
{@code non-null;} an appropriately-constructed instance

        return new BasicBlock(label, insns.withRegisterOffset(delta),
                              successors, primarySuccessor);