Search in sources :

Example 1 with Try

use of com.android.dex.Code.Try in project jadx by skylot.

the class MethodNode method initTryCatches.

private void initTryCatches(Code mthCode) {
    InsnNode[] insnByOffset = instructions;
    CatchHandler[] catchBlocks = mthCode.getCatchHandlers();
    Try[] tries = mthCode.getTries();
    if (catchBlocks.length == 0 && tries.length == 0) {
        return;
    }
    int hc = 0;
    Set<Integer> addrs = new HashSet<Integer>();
    List<TryCatchBlock> catches = new ArrayList<TryCatchBlock>(catchBlocks.length);
    for (CatchHandler handler : catchBlocks) {
        TryCatchBlock tcBlock = new TryCatchBlock();
        catches.add(tcBlock);
        for (int i = 0; i < handler.getAddresses().length; i++) {
            int addr = handler.getAddresses()[i];
            ClassInfo type = ClassInfo.fromDex(parentClass.dex(), handler.getTypeIndexes()[i]);
            tcBlock.addHandler(this, addr, type);
            addrs.add(addr);
            hc++;
        }
        int addr = handler.getCatchAllAddress();
        if (addr >= 0) {
            tcBlock.addHandler(this, addr, null);
            addrs.add(addr);
            hc++;
        }
    }
    if (hc > 0 && hc != addrs.size()) {
        // each handler must be only in one try/catch block
        for (TryCatchBlock ct1 : catches) {
            for (TryCatchBlock ct2 : catches) {
                if (ct1 != ct2 && ct2.containsAllHandlers(ct1)) {
                    for (ExceptionHandler h : ct1.getHandlers()) {
                        ct2.removeHandler(this, h);
                        h.setTryBlock(ct1);
                    }
                }
            }
        }
    }
    // attach EXC_HANDLER attributes to instructions
    addrs.clear();
    for (TryCatchBlock ct : catches) {
        for (ExceptionHandler eh : ct.getHandlers()) {
            int addr = eh.getHandleOffset();
            ExcHandlerAttr ehAttr = new ExcHandlerAttr(ct, eh);
            insnByOffset[addr].addAttr(ehAttr);
        }
    }
    // attach TRY_ENTER, TRY_LEAVE attributes to instructions
    for (Try aTry : tries) {
        int catchNum = aTry.getCatchHandlerIndex();
        TryCatchBlock catchBlock = catches.get(catchNum);
        int offset = aTry.getStartAddress();
        int end = offset + aTry.getInstructionCount() - 1;
        InsnNode insn = insnByOffset[offset];
        insn.add(AFlag.TRY_ENTER);
        while (offset <= end && offset >= 0) {
            insn = insnByOffset[offset];
            catchBlock.addInsn(insn);
            offset = InsnDecoder.getNextInsnOffset(insnByOffset, offset);
        }
        if (insnByOffset[end] != null) {
            insnByOffset[end].add(AFlag.TRY_LEAVE);
        } else {
            insn.add(AFlag.TRY_LEAVE);
        }
    }
}
Also used : ExcHandlerAttr(jadx.core.dex.trycatch.ExcHandlerAttr) ArrayList(java.util.ArrayList) CatchHandler(com.android.dex.Code.CatchHandler) ExceptionHandler(jadx.core.dex.trycatch.ExceptionHandler) Try(com.android.dex.Code.Try) TryCatchBlock(jadx.core.dex.trycatch.TryCatchBlock) HashSet(java.util.HashSet) ClassInfo(jadx.core.dex.info.ClassInfo)

Aggregations

CatchHandler (com.android.dex.Code.CatchHandler)1 Try (com.android.dex.Code.Try)1 ClassInfo (jadx.core.dex.info.ClassInfo)1 ExcHandlerAttr (jadx.core.dex.trycatch.ExcHandlerAttr)1 ExceptionHandler (jadx.core.dex.trycatch.ExceptionHandler)1 TryCatchBlock (jadx.core.dex.trycatch.TryCatchBlock)1 ArrayList (java.util.ArrayList)1 HashSet (java.util.HashSet)1