use of jadx.core.dex.nodes.IBranchRegion in project jadx by skylot.
the class ProcessTryCatchRegions method wrapBlocks.
/**
* Extract all block dominated by 'dominator' to separate region and mark as try/catch block
*/
private static boolean wrapBlocks(IRegion replaceRegion, TryCatchBlock tb, BlockNode dominator) {
if (replaceRegion == null) {
return false;
}
if (replaceRegion instanceof LoopRegion) {
LoopRegion loop = (LoopRegion) replaceRegion;
return wrapBlocks(loop.getBody(), tb, dominator);
}
if (replaceRegion instanceof IBranchRegion) {
return wrapBlocks(replaceRegion.getParent(), tb, dominator);
}
Region tryRegion = new Region(replaceRegion);
List<IContainer> subBlocks = replaceRegion.getSubBlocks();
for (IContainer cont : subBlocks) {
if (RegionUtils.hasPathThroughBlock(dominator, cont)) {
if (isHandlerPath(tb, cont)) {
break;
}
tryRegion.getSubBlocks().add(cont);
}
}
if (tryRegion.getSubBlocks().isEmpty()) {
return false;
}
TryCatchRegion tryCatchRegion = new TryCatchRegion(replaceRegion, tryRegion);
tryRegion.setParent(tryCatchRegion);
tryCatchRegion.setTryCatchBlock(tb.getCatchAttr().getTryBlock());
// replace first node by region
IContainer firstNode = tryRegion.getSubBlocks().get(0);
if (!replaceRegion.replaceSubBlock(firstNode, tryCatchRegion)) {
return false;
}
subBlocks.removeAll(tryRegion.getSubBlocks());
// fix parents for tryRegion sub blocks
for (IContainer cont : tryRegion.getSubBlocks()) {
if (cont instanceof AbstractRegion) {
AbstractRegion aReg = (AbstractRegion) cont;
aReg.setParent(tryRegion);
}
}
return true;
}
use of jadx.core.dex.nodes.IBranchRegion in project jadx by skylot.
the class ProcessVariables method calculateOrder.
private static int calculateOrder(IContainer container, Map<IContainer, Integer> regionsOrder, int id, boolean inc) {
if (!(container instanceof IRegion)) {
return id;
}
IRegion region = (IRegion) container;
Integer previous = regionsOrder.put(region, id);
if (previous != null) {
return id;
}
for (IContainer c : region.getSubBlocks()) {
if (c instanceof IBranchRegion) {
// on branch set for all inner regions same order id
id = calculateOrder(c, regionsOrder, inc ? id + 1 : id, false);
} else {
List<IContainer> handlers = RegionUtils.getExcHandlersForRegion(c);
if (!handlers.isEmpty()) {
for (IContainer handler : handlers) {
id = calculateOrder(handler, regionsOrder, inc ? id + 1 : id, inc);
}
}
id = calculateOrder(c, regionsOrder, inc ? id + 1 : id, inc);
}
}
return id;
}
use of jadx.core.dex.nodes.IBranchRegion in project jadx by skylot.
the class RegionUtils method hasExitEdge.
public static boolean hasExitEdge(IContainer container) {
if (container instanceof IBlock) {
InsnNode lastInsn = BlockUtils.getLastInsn((IBlock) container);
if (lastInsn == null) {
return false;
}
InsnType type = lastInsn.getType();
return type == InsnType.RETURN || type == InsnType.CONTINUE || type == InsnType.BREAK || type == InsnType.THROW;
} else if (container instanceof IBranchRegion) {
for (IContainer br : ((IBranchRegion) container).getBranches()) {
if (br == null || !hasExitEdge(br)) {
return false;
}
}
return true;
} else if (container instanceof IRegion) {
IRegion region = (IRegion) container;
List<IContainer> blocks = region.getSubBlocks();
return !blocks.isEmpty() && hasExitEdge(blocks.get(blocks.size() - 1));
} else {
throw new JadxRuntimeException(unknownContainerType(container));
}
}
use of jadx.core.dex.nodes.IBranchRegion in project jadx by skylot.
the class RegionUtils method getLastInsn.
public static InsnNode getLastInsn(IContainer container) {
if (container instanceof IBlock) {
IBlock block = (IBlock) container;
List<InsnNode> insnList = block.getInstructions();
if (insnList.isEmpty()) {
return null;
}
return insnList.get(insnList.size() - 1);
} else if (container instanceof IBranchRegion) {
return null;
} else if (container instanceof IRegion) {
IRegion region = (IRegion) container;
List<IContainer> blocks = region.getSubBlocks();
if (blocks.isEmpty()) {
return null;
}
return getLastInsn(blocks.get(blocks.size() - 1));
} else {
throw new JadxRuntimeException(unknownContainerType(container));
}
}
Aggregations