mirror of
https://git.huckle.dev/Huckles-Minecraft-Archive/jpexs-decompiler.git
synced 2026-09-25 05:10:47 +00:00
AS3: Editing exceptions
This commit is contained in:
@@ -337,8 +337,12 @@ public class AVM2Code {
|
||||
return null;
|
||||
}
|
||||
|
||||
public String toASMSource(ConstantPool constants) {
|
||||
public String toASMSource(ConstantPool constants,MethodBody body) {
|
||||
String ret = "";
|
||||
for(int e=0;e<body.exceptions.length;e++){
|
||||
ret+="exception "+e+" m["+body.exceptions[e].name_index+"]\""+Helper.escapeString(body.exceptions[e].getVarName(constants))+"\" "+
|
||||
"m["+body.exceptions[e].type_index+"]\""+Helper.escapeString(body.exceptions[e].getTypeName(constants))+"\"\n";
|
||||
}
|
||||
List<Long> offsets = new ArrayList<Long>();
|
||||
for (AVM2Instruction ins : code) {
|
||||
offsets.addAll(ins.getOffsets());
|
||||
@@ -348,6 +352,17 @@ public class AVM2Code {
|
||||
if (offsets.contains(ofs)) {
|
||||
ret += "ofs" + Helper.formatAddress(ofs) + ":";
|
||||
}
|
||||
for(int e=0;e<body.exceptions.length;e++){
|
||||
if(body.exceptions[e].start==ofs){
|
||||
ret+="exceptionstart "+e+":";
|
||||
}
|
||||
if(body.exceptions[e].end==ofs){
|
||||
ret+="exceptionend "+e+":";
|
||||
}
|
||||
if(body.exceptions[e].target==ofs){
|
||||
ret+="exceptiontarget "+e+":";
|
||||
}
|
||||
}
|
||||
ret += ins.toStringNoAddress(constants) + "\n";
|
||||
ofs += ins.getBytes().length;
|
||||
}
|
||||
|
||||
@@ -22,6 +22,8 @@ import com.jpexs.asdec.abc.avm2.AVM2Code;
|
||||
import com.jpexs.asdec.abc.avm2.ConstantPool;
|
||||
import com.jpexs.asdec.abc.avm2.instructions.AVM2Instruction;
|
||||
import com.jpexs.asdec.abc.avm2.instructions.InstructionDefinition;
|
||||
import com.jpexs.asdec.abc.types.ABCException;
|
||||
import com.jpexs.asdec.abc.types.MethodBody;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
@@ -62,15 +64,17 @@ public class ASM3Parser {
|
||||
}
|
||||
}
|
||||
|
||||
public static AVM2Code parse(InputStream is, ConstantPool constants) throws IOException, ParseException {
|
||||
return parse(is, constants, null);
|
||||
public static AVM2Code parse(InputStream is, ConstantPool constants,MethodBody body) throws IOException, ParseException {
|
||||
return parse(is, constants, null,body);
|
||||
}
|
||||
|
||||
public static AVM2Code parse(InputStream is, ConstantPool constants, MissingSymbolHandler missingHandler) throws IOException, ParseException {
|
||||
public static AVM2Code parse(InputStream is, ConstantPool constants, MissingSymbolHandler missingHandler,MethodBody body) throws IOException, ParseException {
|
||||
AVM2Code code = new AVM2Code();
|
||||
|
||||
List<OffsetItem> offsetItems = new ArrayList<OffsetItem>();
|
||||
List<LabelItem> labelItems = new ArrayList<LabelItem>();
|
||||
List<ABCException> exceptions=new ArrayList<ABCException>();
|
||||
List<Integer> exceptionIndices=new ArrayList<Integer>();
|
||||
int offset = 0;
|
||||
|
||||
Flasm3Lexer lexer = new Flasm3Lexer(is);
|
||||
@@ -79,6 +83,33 @@ public class ASM3Parser {
|
||||
AVM2Instruction lastIns = null;
|
||||
do {
|
||||
symb = lexer.yylex();
|
||||
if (symb.type == ParsedSymbol.TYPE_EXCEPTION_START){
|
||||
int exIndex=(Integer)symb.value;
|
||||
int listIndex=exceptionIndices.indexOf(exIndex);
|
||||
if(listIndex==-1){
|
||||
throw new ParseException("Undefinex exception index", lexer.yyline());
|
||||
}
|
||||
exceptions.get(listIndex).start=offset;
|
||||
continue;
|
||||
}
|
||||
if (symb.type == ParsedSymbol.TYPE_EXCEPTION_END){
|
||||
int exIndex=(Integer)symb.value;
|
||||
int listIndex=exceptionIndices.indexOf(exIndex);
|
||||
if(listIndex==-1){
|
||||
throw new ParseException("Undefinex exception index", lexer.yyline());
|
||||
}
|
||||
exceptions.get(listIndex).end=offset;
|
||||
continue;
|
||||
}
|
||||
if (symb.type == ParsedSymbol.TYPE_EXCEPTION_TARGET){
|
||||
int exIndex=(Integer)symb.value;
|
||||
int listIndex=exceptionIndices.indexOf(exIndex);
|
||||
if(listIndex==-1){
|
||||
throw new ParseException("Undefinex exception index", lexer.yyline());
|
||||
}
|
||||
exceptions.get(listIndex).target=offset;
|
||||
continue;
|
||||
}
|
||||
if (symb.type == ParsedSymbol.TYPE_EOF) break;
|
||||
if (symb.type == ParsedSymbol.TYPE_COMMENT) {
|
||||
if (lastIns != null) {
|
||||
@@ -87,6 +118,26 @@ public class ASM3Parser {
|
||||
continue;
|
||||
}
|
||||
if (symb.type == ParsedSymbol.TYPE_INSTRUCTION_NAME) {
|
||||
if(((String)symb.value).toLowerCase().equals("exception")){
|
||||
ParsedSymbol exIndex = lexer.yylex();
|
||||
if (exIndex.type != ParsedSymbol.TYPE_INTEGER) {
|
||||
throw new ParseException("Index expected", lexer.yyline());
|
||||
}
|
||||
ParsedSymbol exName = lexer.yylex();
|
||||
if (exName.type != ParsedSymbol.TYPE_MULTINAME) {
|
||||
throw new ParseException("Multiname expected", lexer.yyline());
|
||||
}
|
||||
ParsedSymbol exType = lexer.yylex();
|
||||
if (exType.type != ParsedSymbol.TYPE_MULTINAME) {
|
||||
throw new ParseException("Multiname expected", lexer.yyline());
|
||||
}
|
||||
ABCException ex=new ABCException();
|
||||
ex.name_index=(int) (long) (Long)exName.value;
|
||||
ex.type_index=(int) (long) (Long)exType.value;
|
||||
exceptions.add(ex);
|
||||
exceptionIndices.add((int)(long)(Long)exIndex.value);
|
||||
continue;
|
||||
}
|
||||
boolean insFound = false;
|
||||
for (InstructionDefinition def : AVM2Code.instructionSet) {
|
||||
if (def.instructionName.equals((String) symb.value)) {
|
||||
@@ -251,207 +302,10 @@ public class ASM3Parser {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* BufferedReader br = new BufferedReader(new InputStreamReader(is));
|
||||
String s = "";
|
||||
Pattern patInsName = Pattern.compile("^([a-z0-9_]+) ");
|
||||
Pattern patLabelName = Pattern.compile("^([a-zA-Z_0-9]+): ");
|
||||
Pattern patInt = Pattern.compile("^([+-]?[0-9]+) ");
|
||||
Pattern patDouble = Pattern.compile("^([+-]?[0-9e.]+) ");
|
||||
Pattern patMultiname = Pattern.compile("^m\\[([0-9]+)\\]\"[^\"]*\" ");
|
||||
Pattern patString = Pattern.compile("\"([^\"]*)\" ");
|
||||
Pattern patofs = Pattern.compile("^([a-zA-Z_0-9]+) ");
|
||||
|
||||
|
||||
long line = 0;
|
||||
|
||||
while ((s = br.readLine()) != null) {
|
||||
line++;
|
||||
s += " ";
|
||||
Matcher m = patInsName.matcher(s);
|
||||
if (m.find()) {
|
||||
String insName = m.group(1);
|
||||
boolean insFound = false;
|
||||
for (InstructionDefinition def : AVM2Code.instructionSet) {
|
||||
if (def.instructionName.equals(insName)) {
|
||||
insFound = true;
|
||||
s = s.substring(insName.length() + 1);
|
||||
List<Integer> operandsList = new ArrayList<Integer>();
|
||||
|
||||
for (int i = 0; i < def.operands.length; i++) {
|
||||
switch (def.operands[i]) {
|
||||
case AVM2Code.DAT_MULTINAME_INDEX:
|
||||
m = patMultiname.matcher(s);
|
||||
if (m.find()) {
|
||||
operandsList.add(Integer.parseInt(m.group(1)));
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid multiname", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_STRING_INDEX:
|
||||
m = patString.matcher(s);
|
||||
if (m.find()) {
|
||||
String str = m.group(1);
|
||||
int sid = constants.getStringId(str);
|
||||
if (sid == 0) {
|
||||
if((missingHandler!=null)&&(missingHandler.missingString(str))){
|
||||
sid=constants.addString(str);
|
||||
}else{
|
||||
throw new ParseException("Unknown String", line);
|
||||
}
|
||||
}
|
||||
operandsList.add(sid);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid String", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_INT_INDEX:
|
||||
m = patInt.matcher(s);
|
||||
if (m.find()) {
|
||||
long intVal=Integer.parseInt(m.group(1));
|
||||
int iid = constants.getIntId(intVal);
|
||||
if (iid == 0) {
|
||||
if((missingHandler!=null)&&(missingHandler.missingInt(intVal))){
|
||||
iid=constants.addInt(intVal);
|
||||
}else{
|
||||
throw new ParseException("Unknown int", line);
|
||||
}
|
||||
}
|
||||
operandsList.add(iid);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid int value", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_UINT_INDEX:
|
||||
m = patInt.matcher(s);
|
||||
if (m.find()) {
|
||||
long intVal=Integer.parseInt(m.group(1));
|
||||
int iid = constants.getUIntId(intVal);
|
||||
if (iid == 0) {
|
||||
if((missingHandler!=null)&&(missingHandler.missingUInt(intVal))){
|
||||
iid=constants.addUInt(intVal);
|
||||
}else{
|
||||
throw new ParseException("Unknown uint", line);
|
||||
}
|
||||
}
|
||||
operandsList.add(iid);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid uint value", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_DOUBLE_INDEX:
|
||||
m = patDouble.matcher(s);
|
||||
if (m.find()) {
|
||||
double doubleVal=Double.parseDouble(m.group(1));
|
||||
int did = constants.getDoubleId(doubleVal);
|
||||
if (did == 0) {
|
||||
if((missingHandler!=null)&&(missingHandler.missingDouble(doubleVal))){
|
||||
did=constants.addDouble(doubleVal);
|
||||
}else{
|
||||
throw new ParseException("Unknown double", line);
|
||||
}
|
||||
}
|
||||
operandsList.add(did);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid double value", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_OFFSET:
|
||||
m = patofs.matcher(s);
|
||||
if (m.find()) {
|
||||
offsetItems.add(new OffsetItem(m.group(1), code.code.size(), i));
|
||||
operandsList.add(0);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid offset value", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.DAT_CASE_BASEOFFSET:
|
||||
m = patofs.matcher(s);
|
||||
if (m.find()) {
|
||||
offsetItems.add(new CaseOffsetItem(m.group(1), code.code.size(), i));
|
||||
operandsList.add(0);
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid offset value", line);
|
||||
}
|
||||
break;
|
||||
case AVM2Code.OPT_CASE_OFFSETS:
|
||||
m = patInt.matcher(s);
|
||||
if (m.find()) {
|
||||
int patCount = Integer.parseInt(m.group(1));
|
||||
operandsList.add(patCount);
|
||||
s = s.substring(m.group(0).length());
|
||||
m = patofs.matcher(s);
|
||||
int k = 1;
|
||||
for (int c = 0; c <= patCount; c++) {
|
||||
if (m.find()) {
|
||||
offsetItems.add(new CaseOffsetItem(m.group(1), code.code.size(), i + k));
|
||||
operandsList.add(0);
|
||||
s = s.substring(m.group(0).length());
|
||||
m = patofs.matcher(s);
|
||||
k++;
|
||||
} else {
|
||||
throw new ParseException("Invalid case count", line);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
throw new ParseException("Invalid case count", line);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
m = patInt.matcher(s);
|
||||
if (m.find()) {
|
||||
operandsList.add(Integer.parseInt(m.group(1)));
|
||||
s = s.substring(m.group(0).length());
|
||||
} else {
|
||||
throw new ParseException("Invalid value", line);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int operands[] = new int[operandsList.size()];
|
||||
for (int i = 0; i < operandsList.size(); i++) {
|
||||
operands[i] = operandsList.get(i);
|
||||
}
|
||||
AVM2Instruction ins = new AVM2Instruction(offset, def, operands, new byte[0]);
|
||||
code.code.add(ins);
|
||||
offset += ins.getBytes().length;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!insFound) {
|
||||
throw new ParseException("Invalid instruction name:" + insName, line);
|
||||
}
|
||||
} else {
|
||||
m = patLabelName.matcher(s);
|
||||
if (m.find()) {
|
||||
labelItems.add(new LabelItem(m.group(1), offset));
|
||||
} else {
|
||||
throw new ParseException("Invalid instruction name", line);
|
||||
}
|
||||
}
|
||||
body.exceptions=new ABCException[exceptions.size()];
|
||||
for(int e=0;e<exceptions.size();e++){
|
||||
body.exceptions[e]=exceptions.get(e);
|
||||
}
|
||||
|
||||
for (OffsetItem oi : offsetItems) {
|
||||
for (LabelItem li : labelItems) {
|
||||
if (oi.label.equals(li.label)) {
|
||||
AVM2Instruction ins = code.code.get((int) oi.insPosition);
|
||||
int relOffset = 0;
|
||||
if (oi instanceof CaseOffsetItem) {
|
||||
relOffset = li.offset - (int) ins.offset;
|
||||
} else {
|
||||
relOffset = li.offset - ((int) ins.offset + ins.getBytes().length);
|
||||
}
|
||||
ins.operands[oi.insOperandIndex] = relOffset;
|
||||
}
|
||||
}
|
||||
}*/
|
||||
return code;
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -32,6 +32,9 @@ public class ParsedSymbol {
|
||||
public static final int TYPE_EOF = 7;
|
||||
public static final int TYPE_LABEL = 8;
|
||||
public static final int TYPE_COMMENT = 9;
|
||||
public static final int TYPE_EXCEPTION_START=10;
|
||||
public static final int TYPE_EXCEPTION_END=11;
|
||||
public static final int TYPE_EXCEPTION_TARGET=12;
|
||||
|
||||
public ParsedSymbol(int type, Object value) {
|
||||
this.type = type;
|
||||
|
||||
@@ -61,6 +61,8 @@ Label = {Identifier}:
|
||||
|
||||
/* integer literals */
|
||||
NumberLiteral = 0 | -?[1-9][0-9]*
|
||||
|
||||
PositiveNumberLiteral = 0 | [1-9][0-9]*
|
||||
|
||||
/* floating point literals */
|
||||
FloatLiteral = -?({FLit1}|{FLit2}|{FLit3}) {Exponent}?
|
||||
@@ -75,6 +77,10 @@ OctDigit = [0-7]
|
||||
/* string and character literals */
|
||||
StringCharacter = [^\r\n\"\\]
|
||||
|
||||
ExceptionStart = "exceptionstart "{PositiveNumberLiteral}":"
|
||||
ExceptionEnd = "exceptionend "{PositiveNumberLiteral}":"
|
||||
ExceptionTarget = "exceptiontarget "{PositiveNumberLiteral}":"
|
||||
|
||||
%state STRING,PARAMETERS
|
||||
|
||||
%%
|
||||
@@ -85,6 +91,18 @@ StringCharacter = [^\r\n\"\\]
|
||||
/* whitespace */
|
||||
{WhiteSpace} { }
|
||||
|
||||
{ExceptionStart} {
|
||||
String s=yytext();
|
||||
return new ParsedSymbol(ParsedSymbol.TYPE_EXCEPTION_START,Integer.parseInt(s.substring(15,s.length()-1)));
|
||||
}
|
||||
{ExceptionEnd} {
|
||||
String s=yytext();
|
||||
return new ParsedSymbol(ParsedSymbol.TYPE_EXCEPTION_END,Integer.parseInt(s.substring(13,s.length()-1)));
|
||||
}
|
||||
{ExceptionTarget} {
|
||||
String s=yytext();
|
||||
return new ParsedSymbol(ParsedSymbol.TYPE_EXCEPTION_TARGET,Integer.parseInt(s.substring(16,s.length()-1)));
|
||||
}
|
||||
{Label} {
|
||||
String s=yytext();
|
||||
return new ParsedSymbol(ParsedSymbol.TYPE_LABEL,s.substring(0,s.length()-1));
|
||||
|
||||
@@ -44,7 +44,7 @@ public class ASMSourceEditorPane extends JEditorPane {
|
||||
public void setBodyIndex(int bodyIndex, ABC abc) {
|
||||
this.bodyIndex = bodyIndex;
|
||||
this.abc = abc;
|
||||
setText(abc.bodies[bodyIndex].code.toASMSource(abc.constants));
|
||||
setText(abc.bodies[bodyIndex].code.toASMSource(abc.constants,abc.bodies[bodyIndex]));
|
||||
}
|
||||
|
||||
public void graph(){
|
||||
@@ -53,7 +53,7 @@ public class ASMSourceEditorPane extends JEditorPane {
|
||||
|
||||
public void save(ConstantPool constants) {
|
||||
try {
|
||||
AVM2Code acode = ASM3Parser.parse(new ByteArrayInputStream(getText().getBytes()), constants, new DialogMissingSymbolHandler());
|
||||
AVM2Code acode = ASM3Parser.parse(new ByteArrayInputStream(getText().getBytes()), constants, new DialogMissingSymbolHandler(),abc.bodies[bodyIndex]);
|
||||
abc.bodies[bodyIndex].code = acode;
|
||||
Main.abcMainFrame.decompiledTextArea.reloadClass();
|
||||
Main.abcMainFrame.decompiledTextArea.gotoLastTrait();
|
||||
@@ -68,14 +68,13 @@ public class ASMSourceEditorPane extends JEditorPane {
|
||||
|
||||
public void verify(ConstantPool constants, ABC abc) {
|
||||
try {
|
||||
AVM2Code acode = ASM3Parser.parse(new ByteArrayInputStream(getText().getBytes()), constants, new DialogMissingSymbolHandler());
|
||||
acode.clearSecureSWF(abc.constants, abc.bodies[bodyIndex]);
|
||||
setText(acode.toASMSource(constants));
|
||||
AVM2Code acode = ASM3Parser.parse(new ByteArrayInputStream(getText().getBytes()), constants, new DialogMissingSymbolHandler(),abc.bodies[bodyIndex]);
|
||||
//acode.clearSecureSWF(abc.constants, abc.bodies[bodyIndex]);
|
||||
setText(acode.toASMSource(constants,abc.bodies[bodyIndex]));
|
||||
|
||||
|
||||
//Main.mainFrame.decompiledTextArea.setBody(mb, abc);
|
||||
} catch (IOException ex) {
|
||||
} catch (ConvertException ex) {
|
||||
} catch (ParseException ex) {
|
||||
JOptionPane.showMessageDialog(this, (ex.text + " on line " + ex.line));
|
||||
selectLine((int) ex.line);
|
||||
|
||||
Reference in New Issue
Block a user