mirror of
https://git.huckle.dev/Huckles-Minecraft-Archive/jpexs-decompiler.git
synced 2026-09-28 16:00:46 +00:00
Issue #862 AS3 asm: do not read beyond return/throw instructions
This commit is contained in:
@@ -282,6 +282,7 @@ import com.jpexs.decompiler.graph.ScopeStack;
|
||||
import com.jpexs.decompiler.graph.TranslateException;
|
||||
import com.jpexs.decompiler.graph.TranslateStack;
|
||||
import com.jpexs.decompiler.graph.TypeItem;
|
||||
import com.jpexs.decompiler.graph.model.ExitItem;
|
||||
import com.jpexs.decompiler.graph.model.LocalData;
|
||||
import com.jpexs.decompiler.graph.model.ScriptEndItem;
|
||||
import com.jpexs.helpers.Helper;
|
||||
@@ -297,6 +298,7 @@ import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.TreeMap;
|
||||
import java.util.TreeSet;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
@@ -675,6 +677,7 @@ public class AVM2Code implements Cloneable {
|
||||
|
||||
public AVM2Code(ABCInputStream ais) throws IOException {
|
||||
Map<Long, AVM2Instruction> codeMap = new TreeMap<>();
|
||||
Map<Long, Long> endOffsets = new HashMap<>();
|
||||
DumpInfo diParent = ais.dumpInfo;
|
||||
List<Long> addresses = new ArrayList<>();
|
||||
long startPos = ais.getPosition();
|
||||
@@ -738,6 +741,11 @@ public class AVM2Code implements Cloneable {
|
||||
}
|
||||
codeMap.put(startOffset, new AVM2Instruction(startOffset, instr, actualOperands));
|
||||
ais.endDumpLevel(instr.instructionCode);
|
||||
long endOffset = ais.getPosition();
|
||||
endOffsets.put(startOffset, endOffset);
|
||||
if (instr.isExitInstruction()) { //do not continue if there is return/throw instruction
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
ais.endDumpLevel();
|
||||
break; // Unknown instructions are ignored (Some of the obfuscators add unknown instructions)
|
||||
@@ -750,6 +758,18 @@ public class AVM2Code implements Cloneable {
|
||||
}
|
||||
}
|
||||
|
||||
//If there are gaps between instructions, fill them with Nops, so the jump offsets are correct
|
||||
List<Long> starts = new ArrayList<>(new TreeSet<>(codeMap.keySet()));
|
||||
for (int s = 0; s < starts.size() - 1/*last does not have next endoffset instruction*/; s++) {
|
||||
long curEnd = endOffsets.get(starts.get(s));
|
||||
if (!codeMap.containsKey(curEnd)) {
|
||||
long nextStart = starts.get(s + 1);
|
||||
for (long off = curEnd; off < nextStart; off++) {
|
||||
codeMap.put(off, new AVM2Instruction(off, new NopIns(), new int[]{}));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
code.addAll(codeMap.values());
|
||||
}
|
||||
|
||||
|
||||
+4
@@ -169,4 +169,8 @@ public class InstructionDefinition implements Serializable {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean isExitInstruction() {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
+6
@@ -45,4 +45,10 @@ public class ReturnValueIns extends InstructionDefinition {
|
||||
public int getStackDelta(AVM2Instruction ins, ABC abc) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExitInstruction() {
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+5
@@ -40,4 +40,9 @@ public class ReturnVoidIns extends InstructionDefinition {
|
||||
public void translate(boolean isStatic, int scriptIndex, int classIndex, HashMap<Integer, GraphTargetItem> localRegs, TranslateStack stack, ScopeStack scopeStack, AVM2ConstantPool constants, AVM2Instruction ins, List<MethodInfo> method_info, List<GraphTargetItem> output, MethodBody body, ABC abc, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames, String path, HashMap<Integer, Integer> localRegsAssignmentIps, int ip, HashMap<Integer, List<Integer>> refs, AVM2Code code) {
|
||||
output.add(new ReturnVoidAVM2Item(ins));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExitInstruction() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
+5
@@ -45,4 +45,9 @@ public class ThrowIns extends InstructionDefinition {
|
||||
public int getStackDelta(AVM2Instruction ins, ABC abc) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExitInstruction() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user