Search in sources :

Example 16 with BlockNode

use of jadx.core.dex.nodes.BlockNode in project jadx by skylot.

the class BlockProcessor method cleanExitNodes.

private static void cleanExitNodes(MethodNode mth) {
    Iterator<BlockNode> iterator = mth.getExitBlocks().iterator();
    while (iterator.hasNext()) {
        BlockNode exitBlock = iterator.next();
        if (exitBlock.getPredecessors().isEmpty()) {
            mth.getBasicBlocks().remove(exitBlock);
            iterator.remove();
        }
    }
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode)

Example 17 with BlockNode

use of jadx.core.dex.nodes.BlockNode in project jadx by skylot.

the class BlockProcessor method modifyBlocksTree.

private static boolean modifyBlocksTree(MethodNode mth) {
    for (BlockNode block : mth.getBasicBlocks()) {
        if (block.getPredecessors().isEmpty() && block != mth.getEnterBlock()) {
            throw new JadxRuntimeException("Unreachable block: " + block);
        }
        // check loops
        List<LoopInfo> loops = block.getAll(AType.LOOP);
        if (loops.size() > 1) {
            boolean oneHeader = true;
            for (LoopInfo loop : loops) {
                if (loop.getStart() != block) {
                    oneHeader = false;
                    break;
                }
            }
            if (oneHeader) {
                // several back edges connected to one loop header => make additional block
                BlockNode newLoopHeader = BlockSplitter.startNewBlock(mth, block.getStartOffset());
                newLoopHeader.add(AFlag.SYNTHETIC);
                connect(newLoopHeader, block);
                for (LoopInfo la : loops) {
                    BlockNode node = la.getEnd();
                    removeConnection(node, block);
                    connect(node, newLoopHeader);
                }
                return true;
            }
        }
        if (loops.size() == 1) {
            LoopInfo loop = loops.get(0);
            // insert additional blocks for possible 'break' insertion
            List<Edge> edges = loop.getExitEdges();
            if (!edges.isEmpty()) {
                boolean change = false;
                for (Edge edge : edges) {
                    BlockNode target = edge.getTarget();
                    if (!target.contains(AFlag.SYNTHETIC)) {
                        BlockSplitter.insertBlockBetween(mth, edge.getSource(), target);
                        change = true;
                    }
                }
                if (change) {
                    return true;
                }
            }
            // insert additional blocks for possible 'continue' insertion
            BlockNode loopEnd = loop.getEnd();
            if (loopEnd.getPredecessors().size() > 1) {
                boolean change = false;
                List<BlockNode> nodes = new ArrayList<BlockNode>(loopEnd.getPredecessors());
                for (BlockNode pred : nodes) {
                    if (!pred.contains(AFlag.SYNTHETIC)) {
                        BlockSplitter.insertBlockBetween(mth, pred, loopEnd);
                        change = true;
                    }
                }
                if (change) {
                    return true;
                }
            }
        }
    }
    return splitReturn(mth);
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) LoopInfo(jadx.core.dex.attributes.nodes.LoopInfo) ArrayList(java.util.ArrayList) JadxRuntimeException(jadx.core.utils.exceptions.JadxRuntimeException) Edge(jadx.core.dex.nodes.Edge)

Example 18 with BlockNode

use of jadx.core.dex.nodes.BlockNode in project jadx by skylot.

the class BlockProcessor method removeBlocks.

private static void removeBlocks(MethodNode mth) {
    Iterator<BlockNode> it = mth.getBasicBlocks().iterator();
    while (it.hasNext()) {
        BlockNode block = it.next();
        if (block.contains(AFlag.REMOVE)) {
            if (!block.getPredecessors().isEmpty() || !block.getSuccessors().isEmpty()) {
                LOG.error("Block {} not deleted, method: {}", block, mth);
            } else {
                CatchAttr catchAttr = block.get(AType.CATCH_BLOCK);
                if (catchAttr != null) {
                    catchAttr.getTryBlock().removeBlock(mth, block);
                }
                it.remove();
            }
        }
    }
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) CatchAttr(jadx.core.dex.trycatch.CatchAttr)

Example 19 with BlockNode

use of jadx.core.dex.nodes.BlockNode in project jadx by skylot.

the class BlockProcessor method isReturnArgAssignInPred.

private static boolean isReturnArgAssignInPred(List<BlockNode> preds, InsnNode returnInsn) {
    RegisterArg arg = (RegisterArg) returnInsn.getArg(0);
    int regNum = arg.getRegNum();
    for (BlockNode pred : preds) {
        for (InsnNode insnNode : pred.getInstructions()) {
            RegisterArg result = insnNode.getResult();
            if (result != null && result.getRegNum() == regNum) {
                return true;
            }
        }
    }
    return false;
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) InsnNode(jadx.core.dex.nodes.InsnNode) RegisterArg(jadx.core.dex.instructions.args.RegisterArg)

Example 20 with BlockNode

use of jadx.core.dex.nodes.BlockNode in project jadx by skylot.

the class BlockSplitter method setupConnections.

private static void setupConnections(MethodNode mth, Map<Integer, BlockNode> blocksMap) {
    for (BlockNode block : mth.getBasicBlocks()) {
        for (InsnNode insn : block.getInstructions()) {
            List<JumpInfo> jumps = insn.getAll(AType.JUMP);
            for (JumpInfo jump : jumps) {
                BlockNode srcBlock = getBlock(jump.getSrc(), blocksMap);
                BlockNode thisBlock = getBlock(jump.getDest(), blocksMap);
                connect(srcBlock, thisBlock);
            }
            connectExceptionHandlers(blocksMap, block, insn);
        }
    }
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) InsnNode(jadx.core.dex.nodes.InsnNode) JumpInfo(jadx.core.dex.attributes.nodes.JumpInfo)

Aggregations

BlockNode (jadx.core.dex.nodes.BlockNode)220 InsnNode (jadx.core.dex.nodes.InsnNode)91 RegisterArg (jadx.core.dex.instructions.args.RegisterArg)43 ArrayList (java.util.ArrayList)41 BitSet (java.util.BitSet)31 JadxRuntimeException (jadx.core.utils.exceptions.JadxRuntimeException)29 InsnArg (jadx.core.dex.instructions.args.InsnArg)25 IndexInsnNode (jadx.core.dex.instructions.IndexInsnNode)21 ExceptionHandler (jadx.core.dex.trycatch.ExceptionHandler)19 PhiInsn (jadx.core.dex.instructions.PhiInsn)14 SSAVar (jadx.core.dex.instructions.args.SSAVar)14 Nullable (org.jetbrains.annotations.Nullable)14 LoopInfo (jadx.core.dex.attributes.nodes.LoopInfo)13 IRegion (jadx.core.dex.nodes.IRegion)13 HashSet (java.util.HashSet)13 MethodNode (jadx.core.dex.nodes.MethodNode)12 Region (jadx.core.dex.regions.Region)12 LoopRegion (jadx.core.dex.regions.loops.LoopRegion)12 InsnType (jadx.core.dex.instructions.InsnType)11 SynchronizedRegion (jadx.core.dex.regions.SynchronizedRegion)11