Commit 6a1717a6 authored by Skylot's avatar Skylot

fix: use original call class for invoke inherited methods (#413)

parent ee6508e9
...@@ -602,12 +602,9 @@ public class InsnGen { ...@@ -602,12 +602,9 @@ public class InsnGen {
// inline method // inline method
MethodNode callMthNode = mth.root().deepResolveMethod(callMth); MethodNode callMthNode = mth.root().deepResolveMethod(callMth);
if (callMthNode != null) { if (callMthNode != null && inlineMethod(callMthNode, insn, code)) {
if (inlineMethod(callMthNode, insn, code)) {
return; return;
} }
callMth = callMthNode.getMethodInfo();
}
int k = 0; int k = 0;
InvokeType type = insn.getInvokeType(); InvokeType type = insn.getInvokeType();
...@@ -640,8 +637,10 @@ public class InsnGen { ...@@ -640,8 +637,10 @@ public class InsnGen {
} }
if (callMthNode != null) { if (callMthNode != null) {
code.attachAnnotation(callMthNode); code.attachAnnotation(callMthNode);
} code.add(callMthNode.getAlias());
} else {
code.add(callMth.getAlias()); code.add(callMth.getAlias());
}
generateMethodArguments(code, insn, k, callMthNode); generateMethodArguments(code, insn, k, callMthNode);
} }
...@@ -694,7 +693,14 @@ public class InsnGen { ...@@ -694,7 +693,14 @@ public class InsnGen {
* Add additional cast for overloaded method argument. * Add additional cast for overloaded method argument.
*/ */
private boolean processOverloadedArg(CodeWriter code, MethodNode callMth, InsnArg arg, int origPos) { private boolean processOverloadedArg(CodeWriter code, MethodNode callMth, InsnArg arg, int origPos) {
ArgType origType = callMth.getArguments(false).get(origPos).getInitType(); ArgType origType;
List<RegisterArg> arguments = callMth.getArguments(false);
if (arguments.isEmpty()) {
mth.addComment("JADX WARN: used method not loaded: " + callMth + ", types can be incorrect");
origType = callMth.getMethodInfo().getArgumentsTypes().get(origPos);
} else {
origType = arguments.get(origPos).getInitType();
}
if (!arg.getType().equals(origType)) { if (!arg.getType().equals(origType)) {
code.add('('); code.add('(');
useType(code, origType); useType(code, origType);
......
...@@ -11,6 +11,7 @@ import jadx.core.dex.instructions.args.ArgType; ...@@ -11,6 +11,7 @@ import jadx.core.dex.instructions.args.ArgType;
import jadx.core.dex.instructions.args.InsnArg; import jadx.core.dex.instructions.args.InsnArg;
import jadx.core.dex.instructions.args.InsnWrapArg; import jadx.core.dex.instructions.args.InsnWrapArg;
import jadx.core.dex.instructions.args.RegisterArg; import jadx.core.dex.instructions.args.RegisterArg;
import jadx.core.dex.instructions.mods.ConstructorInsn;
import jadx.core.dex.nodes.BlockNode; import jadx.core.dex.nodes.BlockNode;
import jadx.core.dex.nodes.ClassNode; import jadx.core.dex.nodes.ClassNode;
import jadx.core.dex.nodes.DexNode; import jadx.core.dex.nodes.DexNode;
...@@ -90,6 +91,9 @@ public class DependencyCollector extends AbstractVisitor { ...@@ -90,6 +91,9 @@ public class DependencyCollector extends AbstractVisitor {
} else if (insn instanceof InvokeNode) { } else if (insn instanceof InvokeNode) {
ClassInfo declClass = ((InvokeNode) insn).getCallMth().getDeclClass(); ClassInfo declClass = ((InvokeNode) insn).getCallMth().getDeclClass();
addDep(dex, depList, declClass); addDep(dex, depList, declClass);
} else if (insn instanceof ConstructorInsn) {
ClassInfo declClass = ((ConstructorInsn) insn).getCallMth().getDeclClass();
addDep(dex, depList, declClass);
} }
} }
......
...@@ -8,7 +8,7 @@ public class CodegenUtils { ...@@ -8,7 +8,7 @@ public class CodegenUtils {
public static void addComments(CodeWriter code, AttrNode node) { public static void addComments(CodeWriter code, AttrNode node) {
for (String comment : node.getAll(AType.COMMENTS)) { for (String comment : node.getAll(AType.COMMENTS)) {
code.startLine("/* ").add(comment).add(" */"); code.startLine("/* ").addMultiLine(comment).add(" */");
} }
} }
} }
package jadx.tests.integration.invoke;
import org.junit.Test;
import jadx.core.dex.nodes.ClassNode;
import jadx.tests.api.IntegrationTest;
import static jadx.tests.api.utils.JadxMatchers.containsOne;
import static org.junit.Assert.assertThat;
public class TestInheritedStaticInvoke extends IntegrationTest {
public static class TestCls {
public static class A {
public static int a() {
return 1;
}
}
public static class B extends A {
}
public int test() {
return B.a(); // not A.a()
}
}
@Test
public void test() {
noDebugInfo();
ClassNode cls = getClassNode(TestCls.class);
String code = cls.getCode().toString();
assertThat(code, containsOne("return B.a();"));
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment