core: improve exceptions handling
This commit is contained in:
@@ -237,7 +237,7 @@ public class ClassGen {
|
||||
if (badCode) {
|
||||
code.startLine("/* JADX WARNING: inconsistent code. */");
|
||||
code.startLine("/* Code decompiled incorrectly, please refer to instructions dump. */");
|
||||
LOG.error(ErrorsCounter.formatErrorMsg(mth, " Inconsistent code"));
|
||||
ErrorsCounter.methodError(mth, "Inconsistent code");
|
||||
}
|
||||
if (mthGen.addDefinition(code)) {
|
||||
code.add(' ');
|
||||
|
||||
@@ -12,29 +12,46 @@ import jadx.core.dex.nodes.InsnNode;
|
||||
import jadx.core.dex.nodes.MethodNode;
|
||||
import jadx.core.utils.exceptions.DecodeException;
|
||||
|
||||
import java.io.EOFException;
|
||||
|
||||
import com.android.dx.io.Code;
|
||||
import com.android.dx.io.OpcodeInfo;
|
||||
import com.android.dx.io.Opcodes;
|
||||
import com.android.dx.io.instructions.DecodedInstruction;
|
||||
import com.android.dx.io.instructions.FillArrayDataPayloadDecodedInstruction;
|
||||
import com.android.dx.io.instructions.PackedSwitchPayloadDecodedInstruction;
|
||||
import com.android.dx.io.instructions.ShortArrayCodeInput;
|
||||
import com.android.dx.io.instructions.SparseSwitchPayloadDecodedInstruction;
|
||||
|
||||
public class InsnDecoder {
|
||||
|
||||
private final MethodNode method;
|
||||
private final DecodedInstruction[] insnArr;
|
||||
private final DexNode dex;
|
||||
private DecodedInstruction[] insnArr;
|
||||
|
||||
public InsnDecoder(MethodNode mthNode, Code mthCode) {
|
||||
public InsnDecoder(MethodNode mthNode) throws DecodeException {
|
||||
this.method = mthNode;
|
||||
this.dex = method.dex();
|
||||
this.insnArr = DecodedInstruction.decodeAll(mthCode.getInstructions());
|
||||
}
|
||||
|
||||
public InsnNode[] run() throws DecodeException {
|
||||
InsnNode[] instructions = new InsnNode[insnArr.length];
|
||||
public void decodeInsns(Code mthCode) throws DecodeException {
|
||||
short[] encodedInstructions = mthCode.getInstructions();
|
||||
int size = encodedInstructions.length;
|
||||
DecodedInstruction[] decoded = new DecodedInstruction[size];
|
||||
ShortArrayCodeInput in = new ShortArrayCodeInput(encodedInstructions);
|
||||
|
||||
try {
|
||||
while (in.hasMore()) {
|
||||
decoded[in.cursor()] = DecodedInstruction.decode(in);
|
||||
}
|
||||
} catch (EOFException e) {
|
||||
throw new DecodeException(method, "", e);
|
||||
}
|
||||
insnArr = decoded;
|
||||
}
|
||||
|
||||
public InsnNode[] process() throws DecodeException {
|
||||
InsnNode[] instructions = new InsnNode[insnArr.length];
|
||||
for (int i = 0; i < insnArr.length; i++) {
|
||||
DecodedInstruction rawInsn = insnArr[i];
|
||||
if (rawInsn != null) {
|
||||
@@ -48,6 +65,7 @@ public class InsnDecoder {
|
||||
instructions[i] = null;
|
||||
}
|
||||
}
|
||||
insnArr = null;
|
||||
return instructions;
|
||||
}
|
||||
|
||||
|
||||
@@ -95,7 +95,7 @@ public class RegisterArg extends InsnArg {
|
||||
InsnNode ai = getAssignInsn();
|
||||
if (ai != null && ai.getType() == InsnType.MOVE) {
|
||||
InsnArg arg = ai.getArg(0);
|
||||
if (arg != this && arg.isThis()) {
|
||||
if (arg != this && "this".equals(arg.getTypedVar().getName())) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ package jadx.core.dex.nodes;
|
||||
import jadx.core.Consts;
|
||||
import jadx.core.codegen.CodeWriter;
|
||||
import jadx.core.dex.attributes.AttributeType;
|
||||
import jadx.core.dex.attributes.JadxErrorAttr;
|
||||
import jadx.core.dex.attributes.LineAttrNode;
|
||||
import jadx.core.dex.attributes.SourceFileAttr;
|
||||
import jadx.core.dex.attributes.annotations.Annotation;
|
||||
@@ -206,7 +207,12 @@ public class ClassNode extends LineAttrNode implements ILoadable {
|
||||
@Override
|
||||
public void load() throws DecodeException {
|
||||
for (MethodNode mth : getMethods()) {
|
||||
mth.load();
|
||||
try {
|
||||
mth.load();
|
||||
} catch (DecodeException e) {
|
||||
LOG.error("Method load error", e);
|
||||
mth.getAttributes().add(new JadxErrorAttr(e));
|
||||
}
|
||||
}
|
||||
for (ClassNode innerCls : getInnerClasses()) {
|
||||
innerCls.load();
|
||||
|
||||
@@ -87,8 +87,9 @@ public class MethodNode extends LineAttrNode implements ILoadable {
|
||||
regsCount = mthCode.getRegistersSize();
|
||||
initMethodTypes();
|
||||
|
||||
InsnDecoder decoder = new InsnDecoder(this, mthCode);
|
||||
InsnNode[] insnByOffset = decoder.run();
|
||||
InsnDecoder decoder = new InsnDecoder(this);
|
||||
decoder.decodeInsns(mthCode);
|
||||
InsnNode[] insnByOffset = decoder.process();
|
||||
instructions = new ArrayList<InsnNode>();
|
||||
for (InsnNode insn : insnByOffset) {
|
||||
if (insn != null) {
|
||||
@@ -113,6 +114,11 @@ public class MethodNode extends LineAttrNode implements ILoadable {
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
if (!noCode) {
|
||||
noCode = true;
|
||||
// load without code
|
||||
load();
|
||||
}
|
||||
throw new DecodeException(this, "Load method exception", e);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,7 +34,9 @@ public class BlockUtils {
|
||||
if (list.size() > 2) {
|
||||
list = cleanBlockList(list);
|
||||
}
|
||||
assert list.size() == 2 : "too many nodes for selectOther: " + node + " in " + list;
|
||||
if (list.size() != 2) {
|
||||
throw new JadxRuntimeException("Incorrect nodes count for selectOther: " + node + " in " + list);
|
||||
}
|
||||
BlockNode first = list.get(0);
|
||||
if (first != node) {
|
||||
return first;
|
||||
|
||||
@@ -66,9 +66,9 @@ public class ErrorsCounter {
|
||||
if (getErrorCount() > 0) {
|
||||
LOG.error(getErrorCount() + " errors occured in following nodes:");
|
||||
for (Object node : ERROR_NODES) {
|
||||
LOG.error(" " + node.getClass().getSimpleName() + ": " + node);
|
||||
String nodeName = node.getClass().getSimpleName().replace("Node", "");
|
||||
LOG.error(" " + nodeName + ": " + node);
|
||||
}
|
||||
// LOG.error("You can run jadx with '-f' option to view low level instructions");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user