AS3: XML filters

This commit is contained in:
Jindra Pet��k
2012-12-31 07:10:21 +01:00
parent 3eb247bbc8
commit de784d1684
7 changed files with 140 additions and 15 deletions
@@ -1418,22 +1418,54 @@ public class AVM2Code {
output.add(new DoWhileTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, loopBody, expression));
} else {
if (expression instanceof InTreeItem) {
boolean found = false;
for (int g = ip + 1; g < jumpPos; g++) {
if (code.get(g).definition instanceof NextValueIns) {
output.add(new ForEachInTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, (InTreeItem) expression, loopBody));
found = true;
break;
TreeItem gti=((InTreeItem) expression).collection.getNotCoerced().getThroughRegister();
if (gti instanceof FilteredCheckTreeItem) {
boolean found = false;
if (loopBody.size() == 1) {
TreeItem ft = loopBody.get(0);
if (ft instanceof WithTreeItem) {
if (((WithTreeItem) ft).items.size() == 1) {
ft = ((WithTreeItem) ft).items.get(0);
if (ft instanceof IfTreeItem) {
IfTreeItem ift = (IfTreeItem) ft;
if (ift.onTrue.size() > 0) {
ft = ift.onTrue.get(0);
if (ft instanceof SetPropertyTreeItem) {
SetPropertyTreeItem spt = (SetPropertyTreeItem) ft;
if (spt.object instanceof LocalRegTreeItem) {
int regIndex = ((LocalRegTreeItem) spt.object).regIndex;
InTreeItem iti=(InTreeItem) expression;
localRegs.put(regIndex, new FilterTreeItem(ins,iti.collection.getThroughRegister(),ift.expression));
found = true;
}
}
}
}
}
}
}
if (code.get(g).definition instanceof NextNameIns) {
output.add(new ForInTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, (InTreeItem) expression, loopBody));
found = true;
break;
if (!found) {
throw new ConvertException("Unknown pattern: bad filter loop", ip);
}
} else {
boolean found = false;
for (int g = ip + 1; g < jumpPos; g++) {
if (code.get(g).definition instanceof NextValueIns) {
output.add(new ForEachInTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, (InTreeItem) expression, loopBody));
found = true;
break;
}
if (code.get(g).definition instanceof NextNameIns) {
output.add(new ForInTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, (InTreeItem) expression, loopBody));
found = true;
break;
}
}
if (!found) {
throw new ConvertException("Unknown pattern: hasnext without nextvalue/nextname", ip);
}
}
if (!found) {
throw new ConvertException("Unknown pattern: hasnext without nextvalue/nextname", ip);
}
} else {
output.add(new WhileTreeItem(ins, currentLoop.loopBreak, currentLoop.loopContinue, expression, loopBody));
@@ -21,6 +21,7 @@ import com.jpexs.asdec.abc.avm2.ConstantPool;
import com.jpexs.asdec.abc.avm2.LocalDataArea;
import com.jpexs.asdec.abc.avm2.instructions.AVM2Instruction;
import com.jpexs.asdec.abc.avm2.instructions.InstructionDefinition;
import com.jpexs.asdec.abc.avm2.treemodel.FilteredCheckTreeItem;
import com.jpexs.asdec.abc.avm2.treemodel.TreeItem;
import com.jpexs.asdec.abc.types.MethodInfo;
import java.util.HashMap;
@@ -40,6 +41,8 @@ public class CheckFilterIns extends InstructionDefinition {
@Override
public void translate(boolean isStatic, int classIndex, java.util.HashMap<Integer, TreeItem> localRegs, Stack<TreeItem> stack, java.util.Stack<TreeItem> scopeStack, ConstantPool constants, AVM2Instruction ins, MethodInfo[] method_info, List<TreeItem> output, com.jpexs.asdec.abc.types.MethodBody body, com.jpexs.asdec.abc.ABC abc, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames) {
TreeItem obj=stack.pop();
stack.push(new FilteredCheckTreeItem(ins, obj));
}
@Override
@@ -0,0 +1,42 @@
/*
* Copyright (C) 2012 JPEXS
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package com.jpexs.asdec.abc.avm2.treemodel;
import com.jpexs.asdec.abc.avm2.ConstantPool;
import com.jpexs.asdec.abc.avm2.instructions.AVM2Instruction;
import java.util.HashMap;
import java.util.List;
/**
*
* @author JPEXS
*/
public class FilteredCheckTreeItem extends TreeItem {
TreeItem object;
public FilteredCheckTreeItem(AVM2Instruction instruction,TreeItem object) {
super(instruction, NOPRECEDENCE);
this.object=object;
}
@Override
public String toString(ConstantPool constants, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames) {
return object.toString(constants, localRegNames, fullyQualifiedNames);
}
}
@@ -18,6 +18,7 @@ package com.jpexs.asdec.abc.avm2.treemodel;
import com.jpexs.asdec.abc.avm2.ConstantPool;
import com.jpexs.asdec.abc.avm2.instructions.AVM2Instruction;
import com.jpexs.asdec.abc.avm2.treemodel.clauses.FilterTreeItem;
import java.util.HashMap;
import java.util.List;
@@ -37,6 +38,9 @@ public class LocalRegTreeItem extends TreeItem {
@Override
public String toString(ConstantPool constants, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames) {
if(computedValue instanceof FilterTreeItem){
return computedValue.toString(constants, localRegNames, fullyQualifiedNames);
}
return hilight(localRegName(localRegNames, regIndex));
}
@@ -32,6 +32,6 @@ public class UnparsedTreeItem extends TreeItem {
@Override
public String toString(ConstantPool constants, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames) {
return hilight(value);
return value;
}
}
@@ -0,0 +1,44 @@
/*
* Copyright (C) 2012 JPEXS
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package com.jpexs.asdec.abc.avm2.treemodel.clauses;
import com.jpexs.asdec.abc.avm2.ConstantPool;
import com.jpexs.asdec.abc.avm2.instructions.AVM2Instruction;
import com.jpexs.asdec.abc.avm2.treemodel.TreeItem;
import java.util.HashMap;
import java.util.List;
/**
*
* @author JPEXS
*/
public class FilterTreeItem extends TreeItem {
public TreeItem expression;
public TreeItem collection;
public FilterTreeItem(AVM2Instruction instruction, TreeItem collection, TreeItem expression) {
super(instruction, NOPRECEDENCE);
this.expression = expression;
this.collection = collection;
}
@Override
public String toString(ConstantPool constants, HashMap<Integer, String> localRegNames, List<String> fullyQualifiedNames) {
return collection.toString(constants, localRegNames, fullyQualifiedNames)+hilight(".(") + expression.toString(constants, localRegNames, fullyQualifiedNames) + hilight(")");
}
}
@@ -198,7 +198,7 @@ public class Multiname {
return "";
}
if (name_index == 0) {
return "*";
return (isAttribute() ? "@*" : "*");
} else {
String name = constants.constant_string[name_index];
if ((fullyQualifiedNames != null) && fullyQualifiedNames.contains(name)) {