Search in sources :

Example 1 with LoopLabelAttr

use of jadx.core.dex.attributes.nodes.LoopLabelAttr in project jadx by skylot.

the class RegionGen method makeLoop.

public void makeLoop(LoopRegion region, ICodeWriter code) throws CodegenException {
    code.startLineWithNum(region.getSourceLine());
    LoopLabelAttr labelAttr = region.getInfo().getStart().get(AType.LOOP_LABEL);
    if (labelAttr != null) {
        code.add(mgen.getNameGen().getLoopLabel(labelAttr)).add(": ");
    }
    IfCondition condition = region.getCondition();
    if (condition == null) {
        // infinite loop
        code.add("while (true) {");
        makeRegionIndent(code, region.getBody());
        code.startLine('}');
        return;
    }
    InsnNode condInsn = condition.getFirstInsn();
    InsnCodeOffset.attach(code, condInsn);
    ConditionGen conditionGen = new ConditionGen(this);
    LoopType type = region.getType();
    if (type != null) {
        if (type instanceof ForLoop) {
            ForLoop forLoop = (ForLoop) type;
            code.add("for (");
            makeInsn(forLoop.getInitInsn(), code, Flags.INLINE);
            code.add("; ");
            conditionGen.add(code, condition);
            code.add("; ");
            makeInsn(forLoop.getIncrInsn(), code, Flags.INLINE);
            code.add(") {");
            CodeGenUtils.addCodeComments(code, mth, condInsn);
            makeRegionIndent(code, region.getBody());
            code.startLine('}');
            return;
        }
        if (type instanceof ForEachLoop) {
            ForEachLoop forEachLoop = (ForEachLoop) type;
            code.add("for (");
            declareVar(code, forEachLoop.getVarArg());
            code.add(" : ");
            addArg(code, forEachLoop.getIterableArg(), false);
            code.add(") {");
            CodeGenUtils.addCodeComments(code, mth, condInsn);
            makeRegionIndent(code, region.getBody());
            code.startLine('}');
            return;
        }
        throw new JadxRuntimeException("Unknown loop type: " + type.getClass());
    }
    if (region.isConditionAtEnd()) {
        code.add("do {");
        CodeGenUtils.addCodeComments(code, mth, condInsn);
        makeRegionIndent(code, region.getBody());
        code.startLineWithNum(region.getSourceLine());
        code.add("} while (");
        conditionGen.add(code, condition);
        code.add(");");
    } else {
        code.add("while (");
        conditionGen.add(code, condition);
        code.add(") {");
        CodeGenUtils.addCodeComments(code, mth, condInsn);
        makeRegionIndent(code, region.getBody());
        code.startLine('}');
    }
}
Also used : InsnNode(jadx.core.dex.nodes.InsnNode) ForLoop(jadx.core.dex.regions.loops.ForLoop) LoopLabelAttr(jadx.core.dex.attributes.nodes.LoopLabelAttr) LoopType(jadx.core.dex.regions.loops.LoopType) JadxRuntimeException(jadx.core.utils.exceptions.JadxRuntimeException) IfCondition(jadx.core.dex.regions.conditions.IfCondition) ForEachLoop(jadx.core.dex.regions.loops.ForEachLoop)

Example 2 with LoopLabelAttr

use of jadx.core.dex.attributes.nodes.LoopLabelAttr in project jadx by skylot.

the class RegionMaker method addBreakLabel.

private void addBreakLabel(Edge exitEdge, BlockNode exit, InsnNode breakInsn) {
    BlockNode outBlock = BlockUtils.getNextBlock(exitEdge.getTarget());
    if (outBlock == null) {
        return;
    }
    List<LoopInfo> exitLoop = mth.getAllLoopsForBlock(outBlock);
    if (!exitLoop.isEmpty()) {
        return;
    }
    List<LoopInfo> inLoops = mth.getAllLoopsForBlock(exitEdge.getSource());
    if (inLoops.size() < 2) {
        return;
    }
    // search for parent loop
    LoopInfo parentLoop = null;
    for (LoopInfo loop : inLoops) {
        if (loop.getParentLoop() == null) {
            parentLoop = loop;
            break;
        }
    }
    if (parentLoop == null) {
        return;
    }
    if (parentLoop.getEnd() != exit && !parentLoop.getExitNodes().contains(exit)) {
        LoopLabelAttr labelAttr = new LoopLabelAttr(parentLoop);
        breakInsn.addAttr(labelAttr);
        parentLoop.getStart().addAttr(labelAttr);
    }
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) LoopInfo(jadx.core.dex.attributes.nodes.LoopInfo) LoopLabelAttr(jadx.core.dex.attributes.nodes.LoopLabelAttr)

Example 3 with LoopLabelAttr

use of jadx.core.dex.attributes.nodes.LoopLabelAttr in project jadx by skylot.

the class RegionGen method makeLoop.

private CodeWriter makeLoop(LoopRegion region, CodeWriter code) throws CodegenException {
    BlockNode header = region.getHeader();
    if (header != null) {
        List<InsnNode> headerInsns = header.getInstructions();
        if (headerInsns.size() > 1) {
            ErrorsCounter.methodError(mth, "Found not inlined instructions from loop header");
            int last = headerInsns.size() - 1;
            for (int i = 0; i < last; i++) {
                InsnNode insn = headerInsns.get(i);
                makeInsn(insn, code);
            }
        }
    }
    LoopLabelAttr labelAttr = region.getInfo().getStart().get(AType.LOOP_LABEL);
    if (labelAttr != null) {
        code.startLine(mgen.getNameGen().getLoopLabel(labelAttr)).add(':');
    }
    IfCondition condition = region.getCondition();
    if (condition == null) {
        // infinite loop
        code.startLine("while (true) {");
        makeRegionIndent(code, region.getBody());
        code.startLine('}');
        return code;
    }
    ConditionGen conditionGen = new ConditionGen(this);
    LoopType type = region.getType();
    if (type != null) {
        if (type instanceof ForLoop) {
            ForLoop forLoop = (ForLoop) type;
            code.startLine("for (");
            makeInsn(forLoop.getInitInsn(), code, Flags.INLINE);
            code.add("; ");
            conditionGen.add(code, condition);
            code.add("; ");
            makeInsn(forLoop.getIncrInsn(), code, Flags.INLINE);
            code.add(") {");
            makeRegionIndent(code, region.getBody());
            code.startLine('}');
            return code;
        }
        if (type instanceof ForEachLoop) {
            ForEachLoop forEachLoop = (ForEachLoop) type;
            code.startLine("for (");
            declareVar(code, forEachLoop.getVarArg());
            code.add(" : ");
            addArg(code, forEachLoop.getIterableArg(), false);
            code.add(") {");
            makeRegionIndent(code, region.getBody());
            code.startLine('}');
            return code;
        }
        throw new JadxRuntimeException("Unknown loop type: " + type.getClass());
    }
    if (region.isConditionAtEnd()) {
        code.startLine("do {");
        makeRegionIndent(code, region.getBody());
        code.startLine("} while (");
        conditionGen.add(code, condition);
        code.add(");");
    } else {
        code.startLine("while (");
        conditionGen.add(code, condition);
        code.add(") {");
        makeRegionIndent(code, region.getBody());
        code.startLine('}');
    }
    return code;
}
Also used : BlockNode(jadx.core.dex.nodes.BlockNode) InsnNode(jadx.core.dex.nodes.InsnNode) ForLoop(jadx.core.dex.regions.loops.ForLoop) LoopLabelAttr(jadx.core.dex.attributes.nodes.LoopLabelAttr) LoopType(jadx.core.dex.regions.loops.LoopType) JadxRuntimeException(jadx.core.utils.exceptions.JadxRuntimeException) IfCondition(jadx.core.dex.regions.conditions.IfCondition) ForEachLoop(jadx.core.dex.regions.loops.ForEachLoop)

Example 4 with LoopLabelAttr

use of jadx.core.dex.attributes.nodes.LoopLabelAttr in project jadx by skylot.

the class InsnGen method makeInsnBody.

private void makeInsnBody(CodeWriter code, InsnNode insn, Set<Flags> state) throws CodegenException {
    switch(insn.getType()) {
        case CONST_STR:
            String str = ((ConstStringNode) insn).getString();
            code.add(mth.dex().root().getStringUtils().unescapeString(str));
            break;
        case CONST_CLASS:
            ArgType clsType = ((ConstClassNode) insn).getClsType();
            useType(code, clsType);
            code.add(".class");
            break;
        case CONST:
            LiteralArg arg = (LiteralArg) insn.getArg(0);
            code.add(lit(arg));
            break;
        case MOVE:
            addArg(code, insn.getArg(0), false);
            break;
        case CHECK_CAST:
        case CAST:
            {
                boolean wrap = state.contains(Flags.BODY_ONLY);
                if (wrap) {
                    code.add('(');
                }
                code.add('(');
                useType(code, (ArgType) ((IndexInsnNode) insn).getIndex());
                code.add(") ");
                addArg(code, insn.getArg(0), true);
                if (wrap) {
                    code.add(')');
                }
                break;
            }
        case ARITH:
            makeArith((ArithNode) insn, code, state);
            break;
        case NEG:
            {
                boolean wrap = state.contains(Flags.BODY_ONLY);
                if (wrap) {
                    code.add('(');
                }
                code.add('-');
                addArg(code, insn.getArg(0));
                if (wrap) {
                    code.add(')');
                }
                break;
            }
        case RETURN:
            if (insn.getArgsCount() != 0) {
                code.add("return ");
                addArg(code, insn.getArg(0), false);
            } else {
                code.add("return");
            }
            break;
        case BREAK:
            code.add("break");
            LoopLabelAttr labelAttr = insn.get(AType.LOOP_LABEL);
            if (labelAttr != null) {
                code.add(' ').add(mgen.getNameGen().getLoopLabel(labelAttr));
            }
            break;
        case CONTINUE:
            code.add("continue");
            break;
        case THROW:
            code.add("throw ");
            addArg(code, insn.getArg(0), true);
            break;
        case CMP_L:
        case CMP_G:
            code.add('(');
            addArg(code, insn.getArg(0));
            code.add(" > ");
            addArg(code, insn.getArg(1));
            code.add(" ? 1 : (");
            addArg(code, insn.getArg(0));
            code.add(" == ");
            addArg(code, insn.getArg(1));
            code.add(" ? 0 : -1))");
            break;
        case INSTANCE_OF:
            {
                boolean wrap = state.contains(Flags.BODY_ONLY);
                if (wrap) {
                    code.add('(');
                }
                addArg(code, insn.getArg(0));
                code.add(" instanceof ");
                useType(code, (ArgType) ((IndexInsnNode) insn).getIndex());
                if (wrap) {
                    code.add(')');
                }
                break;
            }
        case CONSTRUCTOR:
            makeConstructor((ConstructorInsn) insn, code);
            break;
        case INVOKE:
            makeInvoke((InvokeNode) insn, code);
            break;
        case NEW_ARRAY:
            {
                ArgType arrayType = ((NewArrayNode) insn).getArrayType();
                code.add("new ");
                useType(code, arrayType.getArrayRootElement());
                code.add('[');
                addArg(code, insn.getArg(0));
                code.add(']');
                int dim = arrayType.getArrayDimension();
                for (int i = 0; i < dim - 1; i++) {
                    code.add("[]");
                }
                break;
            }
        case ARRAY_LENGTH:
            addArg(code, insn.getArg(0));
            code.add(".length");
            break;
        case FILLED_NEW_ARRAY:
            filledNewArray((FilledNewArrayNode) insn, code);
            break;
        case AGET:
            addArg(code, insn.getArg(0));
            code.add('[');
            addArg(code, insn.getArg(1), false);
            code.add(']');
            break;
        case APUT:
            addArg(code, insn.getArg(0));
            code.add('[');
            addArg(code, insn.getArg(1), false);
            code.add("] = ");
            addArg(code, insn.getArg(2), false);
            break;
        case IGET:
            {
                FieldInfo fieldInfo = (FieldInfo) ((IndexInsnNode) insn).getIndex();
                instanceField(code, fieldInfo, insn.getArg(0));
                break;
            }
        case IPUT:
            {
                FieldInfo fieldInfo = (FieldInfo) ((IndexInsnNode) insn).getIndex();
                instanceField(code, fieldInfo, insn.getArg(1));
                code.add(" = ");
                addArg(code, insn.getArg(0), false);
                break;
            }
        case SGET:
            staticField(code, (FieldInfo) ((IndexInsnNode) insn).getIndex());
            break;
        case SPUT:
            FieldInfo field = (FieldInfo) ((IndexInsnNode) insn).getIndex();
            staticField(code, field);
            code.add(" = ");
            addArg(code, insn.getArg(0), false);
            break;
        case STR_CONCAT:
            boolean wrap = state.contains(Flags.BODY_ONLY);
            if (wrap) {
                code.add('(');
            }
            for (Iterator<InsnArg> it = insn.getArguments().iterator(); it.hasNext(); ) {
                addArg(code, it.next());
                if (it.hasNext()) {
                    code.add(" + ");
                }
            }
            if (wrap) {
                code.add(')');
            }
            break;
        case MONITOR_ENTER:
            if (isFallback()) {
                code.add("monitor-enter(");
                addArg(code, insn.getArg(0));
                code.add(')');
            }
            break;
        case MONITOR_EXIT:
            if (isFallback()) {
                code.add("monitor-exit(");
                addArg(code, insn.getArg(0));
                code.add(')');
            }
            break;
        case TERNARY:
            makeTernary((TernaryInsn) insn, code, state);
            break;
        case ONE_ARG:
            addArg(code, insn.getArg(0));
            break;
        /* fallback mode instructions */
        case IF:
            fallbackOnlyInsn(insn);
            IfNode ifInsn = (IfNode) insn;
            code.add("if (");
            addArg(code, insn.getArg(0));
            code.add(' ');
            code.add(ifInsn.getOp().getSymbol()).add(' ');
            addArg(code, insn.getArg(1));
            code.add(") goto ").add(MethodGen.getLabelName(ifInsn.getTarget()));
            break;
        case GOTO:
            fallbackOnlyInsn(insn);
            code.add("goto ").add(MethodGen.getLabelName(((GotoNode) insn).getTarget()));
            break;
        case MOVE_EXCEPTION:
            fallbackOnlyInsn(insn);
            code.add("move-exception");
            break;
        case SWITCH:
            fallbackOnlyInsn(insn);
            SwitchNode sw = (SwitchNode) insn;
            code.add("switch(");
            addArg(code, insn.getArg(0));
            code.add(") {");
            code.incIndent();
            for (int i = 0; i < sw.getCasesCount(); i++) {
                String key = sw.getKeys()[i].toString();
                code.startLine("case ").add(key).add(": goto ");
                code.add(MethodGen.getLabelName(sw.getTargets()[i])).add(';');
            }
            code.startLine("default: goto ");
            code.add(MethodGen.getLabelName(sw.getDefaultCaseOffset())).add(';');
            code.decIndent();
            code.startLine('}');
            break;
        case FILL_ARRAY:
            fallbackOnlyInsn(insn);
            FillArrayNode arrayNode = (FillArrayNode) insn;
            Object data = arrayNode.getData();
            String arrStr;
            if (data instanceof int[]) {
                arrStr = Arrays.toString((int[]) data);
            } else if (data instanceof short[]) {
                arrStr = Arrays.toString((short[]) data);
            } else if (data instanceof byte[]) {
                arrStr = Arrays.toString((byte[]) data);
            } else if (data instanceof long[]) {
                arrStr = Arrays.toString((long[]) data);
            } else {
                arrStr = "?";
            }
            code.add('{').add(arrStr.substring(1, arrStr.length() - 1)).add('}');
            break;
        case NEW_INSTANCE:
            // only fallback - make new instance in constructor invoke
            fallbackOnlyInsn(insn);
            code.add("new ").add(insn.getResult().getType().toString());
            break;
        case PHI:
        case MERGE:
            fallbackOnlyInsn(insn);
            code.add(insn.getType().toString()).add("(");
            for (InsnArg insnArg : insn.getArguments()) {
                addArg(code, insnArg);
                code.add(' ');
            }
            code.add(")");
            break;
        default:
            throw new CodegenException(mth, "Unknown instruction: " + insn.getType());
    }
}
Also used : ArgType(jadx.core.dex.instructions.args.ArgType) CodegenException(jadx.core.utils.exceptions.CodegenException) LoopLabelAttr(jadx.core.dex.attributes.nodes.LoopLabelAttr) ConstStringNode(jadx.core.dex.instructions.ConstStringNode) LiteralArg(jadx.core.dex.instructions.args.LiteralArg) IfNode(jadx.core.dex.instructions.IfNode) SwitchNode(jadx.core.dex.instructions.SwitchNode) FillArrayNode(jadx.core.dex.instructions.FillArrayNode) InsnArg(jadx.core.dex.instructions.args.InsnArg) ConstClassNode(jadx.core.dex.instructions.ConstClassNode) IndexInsnNode(jadx.core.dex.instructions.IndexInsnNode) FieldInfo(jadx.core.dex.info.FieldInfo) GotoNode(jadx.core.dex.instructions.GotoNode)

Example 5 with LoopLabelAttr

use of jadx.core.dex.attributes.nodes.LoopLabelAttr in project jadx by skylot.

the class InsnGen method makeInsnBody.

private void makeInsnBody(ICodeWriter code, InsnNode insn, Set<Flags> state) throws CodegenException {
    switch(insn.getType()) {
        case CONST_STR:
            String str = ((ConstStringNode) insn).getString();
            code.add(mth.root().getStringUtils().unescapeString(str));
            break;
        case CONST_CLASS:
            ArgType clsType = ((ConstClassNode) insn).getClsType();
            useType(code, clsType);
            code.add(".class");
            break;
        case CONST:
            LiteralArg arg = (LiteralArg) insn.getArg(0);
            code.add(lit(arg));
            break;
        case MOVE:
            addArg(code, insn.getArg(0), false);
            break;
        case CHECK_CAST:
        case CAST:
            {
                boolean wrap = state.contains(Flags.BODY_ONLY);
                if (wrap) {
                    code.add('(');
                }
                code.add('(');
                useType(code, (ArgType) ((IndexInsnNode) insn).getIndex());
                code.add(") ");
                addArg(code, insn.getArg(0), true);
                if (wrap) {
                    code.add(')');
                }
                break;
            }
        case ARITH:
            makeArith((ArithNode) insn, code, state);
            break;
        case NEG:
            oneArgInsn(code, insn, state, '-');
            break;
        case NOT:
            char op = insn.getArg(0).getType() == ArgType.BOOLEAN ? '!' : '~';
            oneArgInsn(code, insn, state, op);
            break;
        case RETURN:
            if (insn.getArgsCount() != 0) {
                code.add("return ");
                addArg(code, insn.getArg(0), false);
            } else {
                code.add("return");
            }
            break;
        case BREAK:
            code.add("break");
            LoopLabelAttr labelAttr = insn.get(AType.LOOP_LABEL);
            if (labelAttr != null) {
                code.add(' ').add(mgen.getNameGen().getLoopLabel(labelAttr));
            }
            break;
        case CONTINUE:
            code.add("continue");
            break;
        case THROW:
            code.add("throw ");
            addArg(code, insn.getArg(0), true);
            break;
        case CMP_L:
        case CMP_G:
            code.add('(');
            addArg(code, insn.getArg(0));
            code.add(" > ");
            addArg(code, insn.getArg(1));
            code.add(" ? 1 : (");
            addArg(code, insn.getArg(0));
            code.add(" == ");
            addArg(code, insn.getArg(1));
            code.add(" ? 0 : -1))");
            break;
        case INSTANCE_OF:
            {
                boolean wrap = state.contains(Flags.BODY_ONLY);
                if (wrap) {
                    code.add('(');
                }
                addArg(code, insn.getArg(0));
                code.add(" instanceof ");
                useType(code, (ArgType) ((IndexInsnNode) insn).getIndex());
                if (wrap) {
                    code.add(')');
                }
                break;
            }
        case CONSTRUCTOR:
            makeConstructor((ConstructorInsn) insn, code);
            break;
        case INVOKE:
            makeInvoke((InvokeNode) insn, code);
            break;
        case NEW_ARRAY:
            {
                ArgType arrayType = ((NewArrayNode) insn).getArrayType();
                code.add("new ");
                useType(code, arrayType.getArrayRootElement());
                int k = 0;
                int argsCount = insn.getArgsCount();
                for (; k < argsCount; k++) {
                    code.add('[');
                    addArg(code, insn.getArg(k), false);
                    code.add(']');
                }
                int dim = arrayType.getArrayDimension();
                for (; k < dim - 1; k++) {
                    code.add("[]");
                }
                break;
            }
        case ARRAY_LENGTH:
            addArg(code, insn.getArg(0));
            code.add(".length");
            break;
        case FILLED_NEW_ARRAY:
            filledNewArray((FilledNewArrayNode) insn, code);
            break;
        case FILL_ARRAY:
            FillArrayInsn arrayNode = (FillArrayInsn) insn;
            if (fallback) {
                String arrStr = arrayNode.dataToString();
                addArg(code, insn.getArg(0));
                code.add(" = {").add(arrStr.substring(1, arrStr.length() - 1)).add("} // fill-array");
            } else {
                fillArray(code, arrayNode);
            }
            break;
        case AGET:
            addArg(code, insn.getArg(0));
            code.add('[');
            addArg(code, insn.getArg(1), false);
            code.add(']');
            break;
        case APUT:
            addArg(code, insn.getArg(0));
            code.add('[');
            addArg(code, insn.getArg(1), false);
            code.add("] = ");
            addArg(code, insn.getArg(2), false);
            break;
        case IGET:
            {
                FieldInfo fieldInfo = (FieldInfo) ((IndexInsnNode) insn).getIndex();
                instanceField(code, fieldInfo, insn.getArg(0));
                break;
            }
        case IPUT:
            {
                FieldInfo fieldInfo = (FieldInfo) ((IndexInsnNode) insn).getIndex();
                instanceField(code, fieldInfo, insn.getArg(1));
                code.add(" = ");
                addArg(code, insn.getArg(0), false);
                break;
            }
        case SGET:
            staticField(code, (FieldInfo) ((IndexInsnNode) insn).getIndex());
            break;
        case SPUT:
            FieldInfo field = (FieldInfo) ((IndexInsnNode) insn).getIndex();
            staticField(code, field);
            code.add(" = ");
            addArg(code, insn.getArg(0), false);
            break;
        case STR_CONCAT:
            boolean wrap = state.contains(Flags.BODY_ONLY);
            if (wrap) {
                code.add('(');
            }
            for (Iterator<InsnArg> it = insn.getArguments().iterator(); it.hasNext(); ) {
                addArg(code, it.next());
                if (it.hasNext()) {
                    code.add(" + ");
                }
            }
            if (wrap) {
                code.add(')');
            }
            break;
        case MONITOR_ENTER:
            if (isFallback()) {
                code.add("monitor-enter(");
                addArg(code, insn.getArg(0));
                code.add(')');
            }
            break;
        case MONITOR_EXIT:
            if (isFallback()) {
                code.add("monitor-exit(");
                if (insn.getArgsCount() == 1) {
                    addArg(code, insn.getArg(0));
                }
                code.add(')');
            }
            break;
        case TERNARY:
            makeTernary((TernaryInsn) insn, code, state);
            break;
        case ONE_ARG:
            addArg(code, insn.getArg(0), state);
            break;
        /* fallback mode instructions */
        case IF:
            fallbackOnlyInsn(insn);
            IfNode ifInsn = (IfNode) insn;
            code.add("if (");
            addArg(code, insn.getArg(0));
            code.add(' ');
            code.add(ifInsn.getOp().getSymbol()).add(' ');
            addArg(code, insn.getArg(1));
            code.add(") goto ").add(MethodGen.getLabelName(ifInsn.getTarget()));
            break;
        case GOTO:
            fallbackOnlyInsn(insn);
            code.add("goto ").add(MethodGen.getLabelName(((GotoNode) insn).getTarget()));
            break;
        case MOVE_EXCEPTION:
            fallbackOnlyInsn(insn);
            code.add("move-exception");
            break;
        case SWITCH:
            fallbackOnlyInsn(insn);
            SwitchInsn sw = (SwitchInsn) insn;
            code.add("switch(");
            addArg(code, insn.getArg(0));
            code.add(") {");
            code.incIndent();
            int[] keys = sw.getKeys();
            int[] targets = sw.getTargets();
            for (int i = 0; i < keys.length; i++) {
                code.startLine("case ").add(Integer.toString(keys[i])).add(": goto ");
                code.add(MethodGen.getLabelName(targets[i])).add(';');
            }
            code.startLine("default: goto ");
            code.add(MethodGen.getLabelName(sw.getDefaultCaseOffset())).add(';');
            code.decIndent();
            code.startLine('}');
            break;
        case NEW_INSTANCE:
            // only fallback - make new instance in constructor invoke
            fallbackOnlyInsn(insn);
            code.add("new ").add(insn.getResult().getInitType().toString());
            break;
        case PHI:
            fallbackOnlyInsn(insn);
            code.add(insn.getType().toString()).add('(');
            for (InsnArg insnArg : insn.getArguments()) {
                addArg(code, insnArg);
                code.add(' ');
            }
            code.add(')');
            break;
        case MOVE_RESULT:
            fallbackOnlyInsn(insn);
            code.add("move-result");
            break;
        case FILL_ARRAY_DATA:
            fallbackOnlyInsn(insn);
            code.add("fill-array " + insn);
            break;
        case SWITCH_DATA:
            fallbackOnlyInsn(insn);
            code.add(insn.toString());
            break;
        case MOVE_MULTI:
            fallbackOnlyInsn(insn);
            int len = insn.getArgsCount();
            for (int i = 0; i < len - 1; i += 2) {
                addArg(code, insn.getArg(i));
                code.add(" = ");
                addArg(code, insn.getArg(i + 1));
                code.add("; ");
            }
            break;
        default:
            throw new CodegenException(mth, "Unknown instruction: " + insn.getType());
    }
}
Also used : ArgType(jadx.core.dex.instructions.args.ArgType) CodegenException(jadx.core.utils.exceptions.CodegenException) LoopLabelAttr(jadx.core.dex.attributes.nodes.LoopLabelAttr) ConstStringNode(jadx.core.dex.instructions.ConstStringNode) LiteralArg(jadx.core.dex.instructions.args.LiteralArg) IfNode(jadx.core.dex.instructions.IfNode) SwitchInsn(jadx.core.dex.instructions.SwitchInsn) FillArrayInsn(jadx.core.dex.instructions.FillArrayInsn) InsnArg(jadx.core.dex.instructions.args.InsnArg) ConstClassNode(jadx.core.dex.instructions.ConstClassNode) IndexInsnNode(jadx.core.dex.instructions.IndexInsnNode) FieldInfo(jadx.core.dex.info.FieldInfo) GotoNode(jadx.core.dex.instructions.GotoNode)

Aggregations

LoopLabelAttr (jadx.core.dex.attributes.nodes.LoopLabelAttr)6 InsnNode (jadx.core.dex.nodes.InsnNode)3 LoopInfo (jadx.core.dex.attributes.nodes.LoopInfo)2 FieldInfo (jadx.core.dex.info.FieldInfo)2 ConstClassNode (jadx.core.dex.instructions.ConstClassNode)2 ConstStringNode (jadx.core.dex.instructions.ConstStringNode)2 GotoNode (jadx.core.dex.instructions.GotoNode)2 IfNode (jadx.core.dex.instructions.IfNode)2 IndexInsnNode (jadx.core.dex.instructions.IndexInsnNode)2 ArgType (jadx.core.dex.instructions.args.ArgType)2 InsnArg (jadx.core.dex.instructions.args.InsnArg)2 LiteralArg (jadx.core.dex.instructions.args.LiteralArg)2 BlockNode (jadx.core.dex.nodes.BlockNode)2 IfCondition (jadx.core.dex.regions.conditions.IfCondition)2 ForEachLoop (jadx.core.dex.regions.loops.ForEachLoop)2 ForLoop (jadx.core.dex.regions.loops.ForLoop)2 LoopType (jadx.core.dex.regions.loops.LoopType)2 CodegenException (jadx.core.utils.exceptions.CodegenException)2 JadxRuntimeException (jadx.core.utils.exceptions.JadxRuntimeException)2 FillArrayInsn (jadx.core.dex.instructions.FillArrayInsn)1