use of jadx.core.dex.instructions.args.InsnArg in project jadx by skylot.
the class MethodInlineVisitor method inlineMth.
private static void inlineMth(MethodNode mth, BlockNode firstBlock, BlockNode returnBlock) {
List<InsnNode> insnList = firstBlock.getInstructions();
if (insnList.isEmpty()) {
// synthetic field getter
BlockNode block = mth.getBasicBlocks().get(1);
InsnNode insn = block.getInstructions().get(0);
// set arg from 'return' instruction
addInlineAttr(mth, InsnNode.wrapArg(insn.getArg(0)));
return;
}
// synthetic field setter or method invoke
if (insnList.size() == 1) {
addInlineAttr(mth, insnList.get(0));
return;
}
// other field operations
if (insnList.size() == 2 && returnBlock.getInstructions().size() == 1 && !mth.getReturnType().equals(ArgType.VOID)) {
InsnNode get = insnList.get(0);
InsnNode put = insnList.get(1);
InsnArg retArg = returnBlock.getInstructions().get(0).getArg(0);
if (get.getType() == InsnType.IGET && put.getType() == InsnType.IPUT && retArg.isRegister() && get.getResult().equalRegisterAndType((RegisterArg) retArg)) {
RegisterArg retReg = (RegisterArg) retArg;
retReg.getSVar().removeUse(retReg);
CodeShrinker.shrinkMethod(mth);
insnList = firstBlock.getInstructions();
if (insnList.size() == 1) {
addInlineAttr(mth, insnList.get(0));
}
}
}
}
use of jadx.core.dex.instructions.args.InsnArg in project jadx by skylot.
the class ClassModifier method removeFieldUsageFromConstructor.
private static boolean removeFieldUsageFromConstructor(MethodNode mth, FieldNode field, ClassNode fieldsCls) {
if (mth.isNoCode() || !mth.getAccessFlags().isConstructor()) {
return false;
}
List<RegisterArg> args = mth.getArguments(false);
if (args.isEmpty() || mth.contains(AFlag.SKIP_FIRST_ARG)) {
return false;
}
RegisterArg arg = args.get(0);
if (!arg.getType().equals(fieldsCls.getClassInfo().getType())) {
return false;
}
BlockNode block = mth.getBasicBlocks().get(0);
List<InsnNode> instructions = block.getInstructions();
if (instructions.isEmpty()) {
return false;
}
InsnNode insn = instructions.get(0);
if (insn.getType() != InsnType.IPUT) {
return false;
}
IndexInsnNode putInsn = (IndexInsnNode) insn;
FieldInfo fieldInfo = (FieldInfo) putInsn.getIndex();
if (!fieldInfo.equals(field.getFieldInfo()) || !putInsn.getArg(0).equals(arg)) {
return false;
}
mth.removeFirstArgument();
InstructionRemover.remove(mth, block, insn);
// other arg usage -> wrap with IGET insn
if (arg.getSVar().getUseCount() != 0) {
InsnNode iget = new IndexInsnNode(InsnType.IGET, fieldInfo, 1);
iget.addArg(insn.getArg(1));
for (InsnArg insnArg : arg.getSVar().getUseList()) {
insnArg.wrapInstruction(iget);
}
}
return true;
}
use of jadx.core.dex.instructions.args.InsnArg in project jadx by skylot.
the class InsnNode method copyCommonParams.
protected <T extends InsnNode> T copyCommonParams(T copy) {
copy.setResult(result);
if (copy.getArgsCount() == 0) {
for (InsnArg arg : this.getArguments()) {
if (arg.isInsnWrap()) {
InsnNode wrapInsn = ((InsnWrapArg) arg).getWrapInsn();
copy.addArg(InsnArg.wrapArg(wrapInsn.copy()));
} else {
copy.addArg(arg);
}
}
}
copy.copyAttributesFrom(this);
copy.copyLines(this);
copy.setOffset(this.getOffset());
return copy;
}
use of jadx.core.dex.instructions.args.InsnArg in project jadx by skylot.
the class InsnDecoder method filledNewArray.
private InsnNode filledNewArray(DecodedInstruction insn, int offset, boolean isRange) {
int resReg = getMoveResultRegister(insnArr, offset);
ArgType arrType = dex.getType(insn.getIndex());
ArgType elType = arrType.getArrayElement();
boolean typeImmutable = elType.isPrimitive();
int regsCount = insn.getRegisterCount();
InsnArg[] regs = new InsnArg[regsCount];
if (isRange) {
int r = insn.getA();
for (int i = 0; i < regsCount; i++) {
regs[i] = InsnArg.reg(r, elType, typeImmutable);
r++;
}
} else {
for (int i = 0; i < regsCount; i++) {
int regNum = InsnUtils.getArg(insn, i);
regs[i] = InsnArg.reg(regNum, elType, typeImmutable);
}
}
InsnNode node = new FilledNewArrayNode(elType, regs.length);
node.setResult(resReg == -1 ? null : InsnArg.reg(resReg, arrType));
for (InsnArg arg : regs) {
node.addArg(arg);
}
return node;
}
use of jadx.core.dex.instructions.args.InsnArg in project jadx by skylot.
the class IfMakerHelper method getNextIfNode.
private static BlockNode getNextIfNode(BlockNode block) {
if (block == null || block.contains(AType.LOOP) || block.contains(AFlag.SKIP)) {
return null;
}
List<InsnNode> insns = block.getInstructions();
if (insns.size() == 1 && insns.get(0).getType() == InsnType.IF) {
return block;
}
// skip this block and search in successors chain
List<BlockNode> successors = block.getSuccessors();
if (successors.size() != 1) {
return null;
}
BlockNode next = successors.get(0);
if (next.getPredecessors().size() != 1) {
return null;
}
boolean pass = true;
if (!insns.isEmpty()) {
// check that all instructions can be inlined
for (InsnNode insn : insns) {
RegisterArg res = insn.getResult();
if (res == null) {
pass = false;
break;
}
List<RegisterArg> useList = res.getSVar().getUseList();
if (useList.size() != 1) {
pass = false;
break;
}
InsnArg arg = useList.get(0);
InsnNode usePlace = arg.getParentInsn();
if (!BlockUtils.blockContains(block, usePlace) && !BlockUtils.blockContains(next, usePlace)) {
pass = false;
break;
}
}
}
if (pass) {
return getNextIfNode(next);
}
return null;
}
Aggregations