AS3 parser: custom namespace modifiers

This commit is contained in:
Jindra Petk
2014-04-13 22:44:12 +02:00
parent 07e43b5bce
commit 47009e2748
12 changed files with 185 additions and 60 deletions

View File

@@ -1066,7 +1066,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
return abc;
}
public void generateClass(int namespace, int initScope, PackageAVM2Item pkg, ClassInfo classInfo, InstanceInfo instanceInfo, SourceGeneratorLocalData localData, boolean isInterface, String name, String superName, GraphTargetItem extendsVal, List<GraphTargetItem> implementsStr, GraphTargetItem constructor, List<GraphTargetItem> traitItems) throws ParseException, CompilationException {
public void generateClass(List<Integer> openedNamespaces,int namespace, int initScope, PackageAVM2Item pkg, ClassInfo classInfo, InstanceInfo instanceInfo, SourceGeneratorLocalData localData, boolean isInterface, String name, String superName, GraphTargetItem extendsVal, List<GraphTargetItem> implementsStr, GraphTargetItem constructor, List<GraphTargetItem> traitItems) throws ParseException, CompilationException {
localData.currentClass = pkg.packageName.isEmpty() ? name : pkg.packageName + "." + name;
List<GraphSourceItem> ret = new ArrayList<>();
if (extendsVal == null && !isInterface) {
@@ -1076,8 +1076,9 @@ public class AVM2SourceGenerator implements SourceGenerator {
Trait[] it = generateTraitsPhase1(pkg, name, superName, false, localData, traitItems, instanceInfo.instance_traits);
Trait[] st = generateTraitsPhase1(pkg, name, superName, true, localData, traitItems, classInfo.static_traits);
generateTraitsPhase2(initScope, pkg, name, superName, false, localData, traitItems, instanceInfo.instance_traits, it);
generateTraitsPhase2(initScope, pkg, name, superName, true, localData, traitItems, classInfo.static_traits, st);
generateTraitsPhase2(pkg.packageName,traitItems, it, openedNamespaces, localData);
generateTraitsPhase3(initScope, pkg, name, superName, false, localData, traitItems, instanceInfo.instance_traits, it);
generateTraitsPhase3(initScope, pkg, name, superName, true, localData, traitItems, classInfo.static_traits, st);
if (constructor == null) {
instanceInfo.iinit_index = method(new ArrayList<MethodBody>(), pkg.packageName, false, new ArrayList<AssignableAVM2Item>(), initScope + 1, false, 0, name, extendsVal != null ? extendsVal.toString() : null, true, localData, new ArrayList<GraphTargetItem>(), new ArrayList<String>(), new ArrayList<GraphTargetItem>(), new ArrayList<GraphTargetItem>(), TypeItem.UNBOUNDED/*?? FIXME*/);
} else {
@@ -1142,7 +1143,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
*/
if (cls instanceof ClassAVM2Item) {
ClassAVM2Item cai = (ClassAVM2Item) cls;
generateClass(namespace, initScope, pkg, ci, ii, localData, false, cai.className, cai.extendsOp.toString(), cai.extendsOp, cai.implementsOp, cai.constructor, cai.traits);
generateClass(cai.openedNamespaces,namespace, initScope, pkg, ci, ii, localData, false, cai.className, cai.extendsOp.toString(), cai.extendsOp, cai.implementsOp, cai.constructor, cai.traits);
if (!cai.isDynamic) {
ii.flags |= InstanceInfo.CLASS_SEALED;
}
@@ -1154,7 +1155,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
}
if (cls instanceof InterfaceAVM2Item) {
InterfaceAVM2Item iai = (InterfaceAVM2Item) cls;
generateClass(namespace, initScope, pkg, ci, ii, localData, true, iai.name, null, null, iai.superInterfaces, null, iai.methods);
generateClass(iai.openedNamespaces,namespace, initScope, pkg, ci, ii, localData, true, iai.name, null, null, iai.superInterfaces, null, iai.methods);
ii.flags |= InstanceInfo.CLASS_INTERFACE;
}
@@ -1629,13 +1630,78 @@ public class AVM2SourceGenerator implements SourceGenerator {
return null;
}
public void generateTraitsPhase2(int initScope, PackageAVM2Item pkg, String className, String superName, boolean generateStatic, SourceGeneratorLocalData localData, List<GraphTargetItem> items, Traits ts, Trait[] traits) throws ParseException, CompilationException {
private int genNs(String custom,int namespace, List<Integer> openedNamespaces, SourceGeneratorLocalData localData){
if(custom!=null){
PropertyAVM2Item prop = new PropertyAVM2Item(null, custom, null, abc, allABCs, openedNamespaces, new ArrayList<MethodBody>());
Reference<ValueKind> value=new Reference<>(null);
prop.resolve(localData, new Reference<String>(""), new Reference<String>(""), new Reference<Integer>(0), value);
namespace = value.getVal().value_index;
}
return namespace;
}
public void generateTraitsPhase2(String pkg,List<GraphTargetItem> items,Trait[] traits, List<Integer> openedNamespaces, SourceGeneratorLocalData localData) throws CompilationException{
for (int k = 0; k < items.size(); k++) {
GraphTargetItem item = items.get(k);
if (traits[k] == null) {
continue;
} else if (item instanceof InterfaceAVM2Item) {
traits[k].name_index = traitName(((InterfaceAVM2Item)item).namespace,((InterfaceAVM2Item)item).name);
} else if (item instanceof ClassAVM2Item) {
traits[k].name_index = traitName(((ClassAVM2Item)item).namespace,((ClassAVM2Item)item).className);
} else if ((item instanceof MethodAVM2Item) || (item instanceof GetterAVM2Item) || (item instanceof SetterAVM2Item)) {
traits[k].name_index = traitName(genNs(((MethodAVM2Item)item).customNamespace,((MethodAVM2Item)item).namespace, openedNamespaces, localData),((MethodAVM2Item)item).functionName);
} else if (item instanceof FunctionAVM2Item) {
traits[k].name_index = traitName(((FunctionAVM2Item)item).namespace,((FunctionAVM2Item)item).functionName);
} else if(item instanceof ConstAVM2Item){
traits[k].name_index = traitName(genNs(((ConstAVM2Item)item).customNamespace,((ConstAVM2Item)item).getNamespace(), openedNamespaces, localData),((ConstAVM2Item)item).var);
} else if(item instanceof SlotAVM2Item){
traits[k].name_index = traitName(genNs(((SlotAVM2Item)item).customNamespace,((SlotAVM2Item)item).getNamespace(), openedNamespaces, localData),((SlotAVM2Item)item).var);
}
}
for (int k = 0; k < items.size(); k++) {
GraphTargetItem item = items.get(k);
if (traits[k] == null) {
continue;
}
if (item instanceof ClassAVM2Item) {
InstanceInfo instanceInfo = abc.instance_info.get(((TraitClass)traits[k]).class_info);
instanceInfo.name_index = abc.constants.addMultiname(new Multiname(Multiname.QNAME, abc.constants.getStringId(((ClassAVM2Item) item).className, true),
abc.constants.getNamespaceId(new Namespace(Namespace.KIND_PACKAGE, abc.constants.getStringId(pkg, true)), 0, true), 0, 0, new ArrayList<Integer>()));
if (((ClassAVM2Item) item).extendsOp != null) {
instanceInfo.super_index = typeName(localData, ((ClassAVM2Item) item).extendsOp);
}else{
instanceInfo.super_index = abc.constants.getMultinameId(new Multiname(Multiname.QNAME, str("Object"), namespace(Namespace.KIND_PACKAGE, ""), 0, 0, new ArrayList<Integer>()), true);
}
instanceInfo.interfaces = new int[((ClassAVM2Item) item).implementsOp.size()];
for(int i=0;i<((ClassAVM2Item) item).implementsOp.size();i++)
{
instanceInfo.interfaces[i] = typeName(localData,((ClassAVM2Item) item).implementsOp.get(i));
}
}
if (item instanceof InterfaceAVM2Item) {
InstanceInfo instanceInfo = abc.instance_info.get(((TraitClass)traits[k]).class_info);
instanceInfo.name_index = abc.constants.addMultiname(new Multiname(Multiname.QNAME, abc.constants.getStringId(((ClassAVM2Item) item).className, true),
abc.constants.getNamespaceId(new Namespace(Namespace.KIND_PACKAGE, abc.constants.getStringId(pkg, true)), 0, true), 0, 0, new ArrayList<Integer>()));
instanceInfo.interfaces = new int[((InterfaceAVM2Item) item).superInterfaces.size()];
for(int i=0;i<((InterfaceAVM2Item) item).superInterfaces.size();i++)
{
instanceInfo.interfaces[i] = typeName(localData,((InterfaceAVM2Item) item).superInterfaces.get(i));
}
}
}
}
public void generateTraitsPhase3(int initScope, PackageAVM2Item pkg, String className, String superName, boolean generateStatic, SourceGeneratorLocalData localData, List<GraphTargetItem> items, Traits ts, Trait[] traits) throws ParseException, CompilationException {
//Note: Names must be generated first before accesed in inner subs
for (int k = 0; k < items.size(); k++) {
GraphTargetItem item = items.get(k);
if (traits[k] == null) {
continue;
}
}
if (item instanceof InterfaceAVM2Item) {
generateClass(((InterfaceAVM2Item) item).namespace, abc.class_info.get(((TraitClass) traits[k]).class_info), abc.instance_info.get(((TraitClass) traits[k]).class_info), initScope, pkg, localData, (InterfaceAVM2Item) item);
}
@@ -1669,7 +1735,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
abc.instance_info.add(ii);
tc.class_info = abc.instance_info.size() - 1;
tc.kindType = Trait.TRAIT_CLASS;
tc.name_index = traitName(((InterfaceAVM2Item) item).namespace, ((InterfaceAVM2Item) item).name);
//tc.name_index = traitName(((InterfaceAVM2Item) item).namespace, ((InterfaceAVM2Item) item).name);
tc.slot_id = slot_id++;
ts.traits.add(tc);
traits[k] = tc;
@@ -1683,17 +1749,18 @@ public class AVM2SourceGenerator implements SourceGenerator {
abc.instance_info.add(instanceInfo);
tc.class_info = abc.instance_info.size() - 1;
instanceInfo.name_index = abc.constants.addMultiname(new Multiname(Multiname.QNAME, abc.constants.getStringId(((ClassAVM2Item) item).className, true),
/*instanceInfo.name_index = abc.constants.addMultiname(new Multiname(Multiname.QNAME, abc.constants.getStringId(((ClassAVM2Item) item).className, true),
abc.constants.getNamespaceId(new Namespace(Namespace.KIND_PACKAGE, abc.constants.getStringId(pkg.packageName, true)), 0, true), 0, 0, new ArrayList<Integer>()));
*/
if (((ClassAVM2Item) item).extendsOp != null) {
/*if (((ClassAVM2Item) item).extendsOp != null) {
instanceInfo.super_index = typeName(localData, ((ClassAVM2Item) item).extendsOp);
} else if (true) { //(!isInterface) {
} else {
instanceInfo.super_index = abc.constants.getMultinameId(new Multiname(Multiname.QNAME, str("Object"), namespace(Namespace.KIND_PACKAGE, ""), 0, 0, new ArrayList<Integer>()), true);
}
}*/
tc.kindType = Trait.TRAIT_CLASS;
tc.name_index = traitName(((ClassAVM2Item) item).namespace, ((ClassAVM2Item) item).className);
// tc.name_index = traitName(((ClassAVM2Item) item).namespace, ((ClassAVM2Item) item).className);
tc.slot_id = slot_id++;
ts.traits.add(tc);
traits[k] = tc;
@@ -1731,7 +1798,9 @@ public class AVM2SourceGenerator implements SourceGenerator {
isNamespace = type.toString().equals("Namespace");
isStatic = cai.isStatic();
}
tsc.name_index = traitName(namespace, var);
if(isNamespace){
tsc.name_index = traitName(namespace, var);
}
tsc.type_index = isNamespace ? 0 : (type == null ? 0 : typeName(localData, type));
ValueKind vk = getValueKind(abc.constants.constant_namespace.get(namespace).kind, type, val);
@@ -1752,7 +1821,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
}
TraitMethodGetterSetter tmgs = new TraitMethodGetterSetter();
tmgs.kindType = (item instanceof MethodAVM2Item) ? Trait.TRAIT_METHOD : ((item instanceof GetterAVM2Item) ? Trait.TRAIT_GETTER : Trait.TRAIT_SETTER);
tmgs.name_index = traitName(((MethodAVM2Item) item).namespace, ((MethodAVM2Item) item).functionName);
//tmgs.name_index = traitName(((MethodAVM2Item) item).namespace, ((MethodAVM2Item) item).functionName);
tmgs.disp_id = 0; //0 = disable override optimization; TODO: handle this
if (mai.isFinal()) {
tmgs.kindFlags |= Trait.ATTR_Final;
@@ -1767,11 +1836,11 @@ public class AVM2SourceGenerator implements SourceGenerator {
TraitFunction tf = new TraitFunction();
tf.slot_id = slot_id++;
tf.kindType = Trait.TRAIT_FUNCTION;
tf.name_index = traitName(((FunctionAVM2Item) item).namespace, ((FunctionAVM2Item) item).functionName);
//tf.name_index = traitName(((FunctionAVM2Item) item).namespace, ((FunctionAVM2Item) item).functionName);
ts.traits.add(tf);
traits[k] = tf;
}
}
}
return traits;
}
@@ -1779,7 +1848,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
public ScriptInfo generateScriptInfo(PackageAVM2Item pkg, SourceGeneratorLocalData localData, List<GraphTargetItem> commands, boolean documentClass) throws ParseException, CompilationException {
ScriptInfo si = new ScriptInfo();
Trait[] traitArr = generateTraitsPhase1(pkg, null, null, false, localData, commands, si.traits);
generateTraitsPhase2(pkg.packageName,commands, traitArr, new ArrayList<Integer>(), localData);
MethodInfo mi = new MethodInfo(new int[0], 0, 0, 0, new ValueKind[0], new int[0]);
MethodBody mb = new MethodBody();
mb.method_info = abc.addMethodInfo(mi);
@@ -1820,7 +1889,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
abc.addMethodBody(mb);
si.init_index = mb.method_info;
localData.pkg = pkg.packageName;
generateTraitsPhase2(traitScope, pkg, null, null, false, localData, commands, si.traits, traitArr);
generateTraitsPhase3(traitScope, pkg, null, null, false, localData, commands, si.traits, traitArr);
return si;
}
@@ -1869,7 +1938,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
return TypeItem.UNBOUNDED;
}
public static boolean searchPrototypeChain(boolean instanceOnly, List<ABC> abcs, String pkg, String obj, String propertyName, Reference<String> outName, Reference<String> outNs, Reference<String> outPropNs, Reference<Integer> outPropNsKind, Reference<String> outPropType) {
public static boolean searchPrototypeChain(boolean instanceOnly, List<ABC> abcs, String pkg, String obj, String propertyName, Reference<String> outName, Reference<String> outNs, Reference<String> outPropNs, Reference<Integer> outPropNsKind, Reference<String> outPropType, Reference<ValueKind> outPropValue) {
for (ABC abc : abcs) {
if (!instanceOnly) {
@@ -1882,6 +1951,10 @@ public class AVM2SourceGenerator implements SourceGenerator {
outPropNs.setVal(t.getName(abc).getNamespace(abc.constants).getName(abc.constants));
outPropNsKind.setVal(t.getName(abc).getNamespace(abc.constants).kind);
outPropType.setVal(getTraitReturnType(abc, t).toString());
if(t instanceof TraitSlotConst){
TraitSlotConst tsc=(TraitSlotConst)t;
outPropValue.setVal(new ValueKind(tsc.value_index, tsc.value_kind));
}
return true;
}
}
@@ -1902,6 +1975,10 @@ public class AVM2SourceGenerator implements SourceGenerator {
outPropNs.setVal(t.getName(abc).getNamespace(abc.constants).getName(abc.constants));
outPropNsKind.setVal(t.getName(abc).getNamespace(abc.constants).kind);
outPropType.setVal(getTraitReturnType(abc, t).toString());
if(t instanceof TraitSlotConst){
TraitSlotConst tsc=(TraitSlotConst)t;
outPropValue.setVal(new ValueKind(tsc.value_index, tsc.value_kind));
}
return true;
}
}
@@ -1914,6 +1991,10 @@ public class AVM2SourceGenerator implements SourceGenerator {
outPropNs.setVal(t.getName(abc).getNamespace(abc.constants).getName(abc.constants));
outPropNsKind.setVal(t.getName(abc).getNamespace(abc.constants).kind);
outPropType.setVal(getTraitReturnType(abc, t).toString());
if(t instanceof TraitSlotConst){
TraitSlotConst tsc=(TraitSlotConst)t;
outPropValue.setVal(new ValueKind(tsc.value_index, tsc.value_kind));
}
return true;
}
}
@@ -1921,7 +2002,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
Multiname superName = abc.constants.constant_multiname.get(ii.super_index);
if (superName != null) {
return searchPrototypeChain(instanceOnly, abcs, superName.getNamespace(abc.constants).getName(abc.constants), superName.getName(abc.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType);
return searchPrototypeChain(instanceOnly, abcs, superName.getNamespace(abc.constants).getName(abc.constants), superName.getName(abc.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType, outPropValue);
} else {
return false;
}

View File

@@ -73,6 +73,7 @@ import com.jpexs.decompiler.flash.abc.avm2.model.operations.URShiftAVM2Item;
import com.jpexs.decompiler.flash.abc.avm2.parser.ParseException;
import com.jpexs.decompiler.flash.abc.types.MethodBody;
import com.jpexs.decompiler.flash.abc.types.Namespace;
import com.jpexs.decompiler.flash.abc.types.traits.Trait;
import com.jpexs.decompiler.flash.action.swf4.ActionIf;
import com.jpexs.decompiler.flash.configuration.Configuration;
import com.jpexs.decompiler.flash.tags.ABCContainerTag;
@@ -296,9 +297,9 @@ public class ActionScriptParser {
return ret;
}
private MethodAVM2Item method(Reference<Boolean> needsActivation, List<String> importedClasses, boolean override, boolean isFinal, GraphTargetItem thisType, List<Integer> openedNamespaces, boolean isStatic, int namespace, boolean withBody, String functionName, boolean isMethod, List<AssignableAVM2Item> variables) throws IOException, ParseException {
private MethodAVM2Item method(String customAccess, Reference<Boolean> needsActivation, List<String> importedClasses, boolean override, boolean isFinal, GraphTargetItem thisType, List<Integer> openedNamespaces, boolean isStatic, int namespace, boolean withBody, String functionName, boolean isMethod, List<AssignableAVM2Item> variables) throws IOException, ParseException {
FunctionAVM2Item f = function(needsActivation, importedClasses, namespace, thisType, openedNamespaces, withBody, functionName, isMethod, variables);
return new MethodAVM2Item(f.needsActivation, f.hasRest, f.line, override, isFinal, isStatic, f.namespace, functionName, f.paramTypes, f.paramNames, f.paramValues, f.body, f.subvariables, f.retType);
return new MethodAVM2Item(customAccess,f.needsActivation, f.hasRest, f.line, override, isFinal, isStatic, f.namespace, functionName, f.paramTypes, f.paramNames, f.paramValues, f.body, f.subvariables, f.retType);
}
private FunctionAVM2Item function(Reference<Boolean> needsActivation, List<String> importedClasses, int namespace, GraphTargetItem thisType, List<Integer> openedNamespaces, boolean withBody, String functionName, boolean isMethod, List<AssignableAVM2Item> variables) throws IOException, ParseException {
@@ -391,27 +392,28 @@ public class ActionScriptParser {
boolean isOverride = false;
boolean isFinal = false;
boolean isDynamic = false;
String customAccess = null;
//TODO: namespace name
//TODO: final, dynamic
while (s.isType(SymbolType.STATIC, SymbolType.PUBLIC, SymbolType.PRIVATE, SymbolType.PROTECTED, SymbolType.OVERRIDE, SymbolType.FINAL, SymbolType.DYNAMIC)) {
while (s.isType(SymbolType.STATIC, SymbolType.PUBLIC, SymbolType.PRIVATE, SymbolType.PROTECTED, SymbolType.OVERRIDE, SymbolType.FINAL, SymbolType.DYNAMIC, SymbolType.IDENTIFIER)) {
if (s.type == SymbolType.FINAL) {
if (isFinal) {
throw new ParseException("Only one final keyword allowed", lexer.yyline());
}
isFinal = true;
}
}else
if (s.type == SymbolType.DYNAMIC) {
if (isDynamic) {
throw new ParseException("Only one dynamic keyword allowed", lexer.yyline());
}
isDynamic = true;
}
}else
if (s.type == SymbolType.OVERRIDE) {
if (isOverride) {
throw new ParseException("Only one override keyword allowed", lexer.yyline());
}
isOverride = true;
}
}else
if (s.type == SymbolType.STATIC) {
if (isInterface) {
throw new ParseException("Interface cannot have static traits", lexer.yyline());
@@ -423,6 +425,9 @@ public class ActionScriptParser {
throw new ParseException("Only one static keyword allowed", lexer.yyline());
}
isStatic = true;
} else if(s.type == SymbolType.IDENTIFIER){
customAccess = s.value.toString();
namespace = -2;
} else {
if (namespace != -1) {
throw new ParseException("Only one access identifier allowed", lexer.yyline());
@@ -475,6 +480,9 @@ public class ActionScriptParser {
} while (s.type == SymbolType.COMMA);
}
expected(s, lexer.yyline(), SymbolType.CURLY_OPEN);
if(customAccess!=null){
throw new ParseException("Class cannot have custom namespace", lexer.yyline());
}
traits.add((classTraits(packageInternalNs, importedClasses, privateNs, isDynamic, isFinal, openedNamespaces, packageName, namespace, false, classTypeStr, extendsTypeStr, implementsTypeStrs, variables)));
expectedType(SymbolType.CURLY_CLOSE);
break;
@@ -506,6 +514,9 @@ public class ActionScriptParser {
} while (s.type == SymbolType.COMMA);
}
expected(s, lexer.yyline(), SymbolType.CURLY_OPEN);
if(customAccess!=null){
throw new ParseException("Interface cannot have custom namespace", lexer.yyline());
}
traits.add((classTraits(packageInternalNs, importedClasses, privateNs, false, isFinal, openedNamespaces, packageName, namespace, true, intTypeStr, null, intExtendsTypeStrs, variables)));
expectedType(SymbolType.CURLY_CLOSE);
break;
@@ -545,29 +556,29 @@ public class ActionScriptParser {
if (isFinal) {
throw new ParseException("Final flag not allowed for constructor", lexer.yyline());
}
constr = (method(new Reference<Boolean>(false), importedClasses, false, false, thisType, openedNamespaces, false, namespace, !isInterface, "", true, variables));
constr = (method(customAccess,new Reference<Boolean>(false), importedClasses, false, false, thisType, openedNamespaces, false, namespace, !isInterface, "", true, variables));
} else {
if (isStatic) {
GraphTargetItem t;
MethodAVM2Item ft = method(new Reference<Boolean>(false), importedClasses, isOverride, isFinal, thisType, openedNamespaces, isStatic, namespace, !isInterface, fname, true, variables);
MethodAVM2Item ft = method(customAccess,new Reference<Boolean>(false), importedClasses, isOverride, isFinal, thisType, openedNamespaces, isStatic, namespace, !isInterface, fname, true, variables);
traits.add(ft);
if (isGetter || isSetter) {
throw new ParseException("Getter or Setter cannot be static", lexer.yyline());
}
} else {
MethodAVM2Item ft = method(new Reference<Boolean>(false), importedClasses, isOverride, isFinal, thisType, openedNamespaces, isStatic, namespace, !isInterface, fname, true, variables);
MethodAVM2Item ft = method(customAccess,new Reference<Boolean>(false), importedClasses, isOverride, isFinal, thisType, openedNamespaces, isStatic, namespace, !isInterface, fname, true, variables);
GraphTargetItem t;
if (isGetter) {
if (!ft.paramTypes.isEmpty()) {
throw new ParseException("Getter can't have any parameters", lexer.yyline());
}
GetterAVM2Item g = new GetterAVM2Item(ft.needsActivation, ft.hasRest, ft.line, ft.isOverride(), ft.isFinal(), isStatic, ft.namespace, ft.functionName, ft.paramTypes, ft.paramNames, ft.paramValues, ft.body, ft.subvariables, ft.retType);
GetterAVM2Item g = new GetterAVM2Item(customAccess,ft.needsActivation, ft.hasRest, ft.line, ft.isOverride(), ft.isFinal(), isStatic, ft.namespace, ft.functionName, ft.paramTypes, ft.paramNames, ft.paramValues, ft.body, ft.subvariables, ft.retType);
t = g;
} else if (isSetter) {
if (ft.paramTypes.size() != 1) {
throw new ParseException("Getter must have exactly one parameter", lexer.yyline());
}
SetterAVM2Item st = new SetterAVM2Item(ft.needsActivation, ft.hasRest, ft.line, ft.isOverride(), ft.isFinal(), isStatic, ft.namespace, ft.functionName, ft.paramTypes, ft.paramNames, ft.paramValues, ft.body, ft.subvariables, ft.retType);
SetterAVM2Item st = new SetterAVM2Item(customAccess,ft.needsActivation, ft.hasRest, ft.line, ft.isOverride(), ft.isFinal(), isStatic, ft.namespace, ft.functionName, ft.paramTypes, ft.paramNames, ft.paramValues, ft.body, ft.subvariables, ft.retType);
t = st;
} else {
t = ft;
@@ -597,7 +608,7 @@ public class ActionScriptParser {
lexer.pushback(s);
}
ConstAVM2Item ns = new ConstAVM2Item(true, namespace, nname, new TypeItem("Namespace"), new StringAVM2Item(null, nval));
ConstAVM2Item ns = new ConstAVM2Item(customAccess,true, namespace, nname, new TypeItem("Namespace"), new StringAVM2Item(null, nval));
traits.add(ns);
break;
case CONST:
@@ -631,9 +642,9 @@ public class ActionScriptParser {
}
GraphTargetItem tar;
if (isConst) {
tar = new ConstAVM2Item(isStatic, namespace, vcname, type, value);
tar = new ConstAVM2Item(customAccess,isStatic, namespace, vcname, type, value);
} else {
tar = new SlotAVM2Item(isStatic, namespace, vcname, type, value);
tar = new SlotAVM2Item(customAccess,isStatic, namespace, vcname, type, value);
}
traits.add(tar);
if (s.type != SymbolType.SEMICOLON) {
@@ -683,9 +694,9 @@ public class ActionScriptParser {
GraphTargetItem constr = traits(importedClasses, privateNs, protectedNs, publicNs, packageInternalNs, protectedStaticNs, openedNamespaces, packageName, classNameStr, isInterface, traits);
if (isInterface) {
return new InterfaceAVM2Item(isFinal, namespace, classNameStr, implementsStr, traits);
return new InterfaceAVM2Item(openedNamespaces,isFinal, namespace, classNameStr, implementsStr, traits);
} else {
return new ClassAVM2Item(protectedNs, isDynamic, isFinal, namespace, classNameStr, extendsStr, implementsStr, constr, traits);
return new ClassAVM2Item(openedNamespaces,protectedNs, isDynamic, isFinal, namespace, classNameStr, extendsStr, implementsStr, constr, traits);
}
}

View File

@@ -24,6 +24,7 @@ import com.jpexs.decompiler.flash.abc.avm2.instructions.executing.CallPropertyIn
import com.jpexs.decompiler.flash.abc.avm2.instructions.other.FindPropertyStrictIns;
import com.jpexs.decompiler.flash.abc.avm2.model.AVM2Item;
import com.jpexs.decompiler.flash.abc.types.MethodBody;
import com.jpexs.decompiler.flash.abc.types.ValueKind;
import com.jpexs.decompiler.flash.helpers.GraphTextWriter;
import com.jpexs.decompiler.graph.CompilationException;
import com.jpexs.decompiler.graph.GraphSourceItem;
@@ -82,7 +83,8 @@ public class CallAVM2Item extends AVM2Item {
Reference<String> outPropNs = new Reference<>("");
Reference<Integer> outPropNsKind = new Reference<>(1);
Reference<String> outPropType = new Reference<>("");
if (AVM2SourceGenerator.searchPrototypeChain(true, allAbcs, pkgName, cname, n.getVariableName(), outName, outNs, outPropNs, outPropNsKind, outPropType)) {
Reference<ValueKind> outPropValue = new Reference<>(null);
if (AVM2SourceGenerator.searchPrototypeChain(true, allAbcs, pkgName, cname, n.getVariableName(), outName, outNs, outPropNs, outPropNsKind, outPropType, outPropValue)) {
NameAVM2Item nobj = new NameAVM2Item(new TypeItem(localData.currentClass), n.line, "this", null, false, n.openedNamespaces);
nobj.setRegNumber(0);
obj = nobj;
@@ -112,7 +114,8 @@ public class CallAVM2Item extends AVM2Item {
Reference<String> outPropNs = new Reference<>("");
Reference<Integer> outPropNsKind = new Reference<>(1);
Reference<String> outPropType = new Reference<>("");
if (AVM2SourceGenerator.searchPrototypeChain(true, allAbcs, pkgName, cname, prop.propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType)) {
Reference<ValueKind> outPropValue = new Reference<>(null);
if (AVM2SourceGenerator.searchPrototypeChain(true, allAbcs, pkgName, cname, prop.propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType, outPropValue)) {
NameAVM2Item nobj = new NameAVM2Item(new TypeItem(localData.currentClass), 0, "this", null, false, new ArrayList<Integer>());
nobj.setRegNumber(0);
obj = nobj;

View File

@@ -37,6 +37,7 @@ public class ClassAVM2Item extends AVM2Item implements Block {
public int protectedNs;
public boolean isDynamic;
public boolean isFinal;
public List<Integer> openedNamespaces;
@Override
public List<List<GraphTargetItem>> getSubs() {
@@ -47,7 +48,7 @@ public class ClassAVM2Item extends AVM2Item implements Block {
return ret;
}
public ClassAVM2Item(int protectedNs, boolean isDynamic, boolean isFinal, int namespace, String className, GraphTargetItem extendsOp, List<GraphTargetItem> implementsOp, GraphTargetItem constructor, List<GraphTargetItem> traits) {
public ClassAVM2Item(List<Integer> openedNamespaces, int protectedNs, boolean isDynamic, boolean isFinal, int namespace, String className, GraphTargetItem extendsOp, List<GraphTargetItem> implementsOp, GraphTargetItem constructor, List<GraphTargetItem> traits) {
super(null, NOPRECEDENCE);
this.protectedNs = protectedNs;
this.className = className;
@@ -58,6 +59,7 @@ public class ClassAVM2Item extends AVM2Item implements Block {
this.namespace = namespace;
this.isDynamic = isDynamic;
this.isFinal = isFinal;
this.openedNamespaces = openedNamespaces;
}
@Override

View File

@@ -31,6 +31,7 @@ public class ConstAVM2Item extends AVM2Item {
private boolean isStatic;
public String var;
public GraphTargetItem type;
public String customNamespace;
public int getNamespace() {
return namespace;
@@ -40,13 +41,14 @@ public class ConstAVM2Item extends AVM2Item {
return isStatic;
}
public ConstAVM2Item(boolean isStatic, int namespace, String var, GraphTargetItem type, GraphTargetItem value) {
public ConstAVM2Item(String customNamespace,boolean isStatic, int namespace, String var, GraphTargetItem type, GraphTargetItem value) {
super(null, NOPRECEDENCE);
this.namespace = namespace;
this.value = value;
this.isStatic = isStatic;
this.var = var;
this.type = type;
this.customNamespace = customNamespace;
}
@Override

View File

@@ -25,8 +25,8 @@ import java.util.List;
*/
public class GetterAVM2Item extends MethodAVM2Item {
public GetterAVM2Item(boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
super(needsActivation, hasRest, line, override, isFinal, isStatic, namespace, methodName, paramTypes, paramNames, paramValues, body, subvariables, retType);
public GetterAVM2Item(String customNamespace, boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
super(customNamespace,needsActivation, hasRest, line, override, isFinal, isStatic, namespace, methodName, paramTypes, paramNames, paramValues, body, subvariables, retType);
}
}

View File

@@ -34,14 +34,16 @@ public class InterfaceAVM2Item extends AVM2Item {
public List<GraphTargetItem> methods;
public int namespace;
public boolean isFinal;
public List<Integer> openedNamespaces;
public InterfaceAVM2Item(boolean isFinal, int namespace, String name, List<GraphTargetItem> superInterfaces, List<GraphTargetItem> traits) {
public InterfaceAVM2Item(List<Integer> openedNamespaces, boolean isFinal, int namespace, String name, List<GraphTargetItem> superInterfaces, List<GraphTargetItem> traits) {
super(null, NOPRECEDENCE);
this.name = name;
this.superInterfaces = superInterfaces;
this.methods = traits;
this.namespace = namespace;
this.isFinal = isFinal;
this.openedNamespaces = openedNamespaces;
}
@Override

View File

@@ -30,12 +30,14 @@ public class MethodAVM2Item extends FunctionAVM2Item {
private boolean isStatic;
private boolean isFinal;
private boolean override;
public String customNamespace;
public MethodAVM2Item(boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
public MethodAVM2Item(String customNamespace, boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
super(needsActivation, namespace, hasRest, line, methodName, paramTypes, paramNames, paramValues, body, subvariables, retType);
this.isStatic = isStatic;
this.override = override;
this.isFinal = isFinal;
this.customNamespace = customNamespace;
}
public boolean isOverride() {

View File

@@ -36,6 +36,7 @@ import com.jpexs.decompiler.flash.abc.types.MethodBody;
import com.jpexs.decompiler.flash.abc.types.Multiname;
import com.jpexs.decompiler.flash.abc.types.Namespace;
import com.jpexs.decompiler.flash.abc.types.NamespaceSet;
import com.jpexs.decompiler.flash.abc.types.ValueKind;
import com.jpexs.decompiler.flash.abc.types.traits.Trait;
import com.jpexs.decompiler.flash.abc.types.traits.TraitSlotConst;
import com.jpexs.decompiler.flash.helpers.GraphTextWriter;
@@ -93,9 +94,10 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
return abc.constants.getNamespaceSetId(new NamespaceSet(nssa), true);
}
private void resolve(SourceGeneratorLocalData localData, Reference<String> objectType, Reference<String> propertyType, Reference<Integer> propertyIndex) {
public void resolve(SourceGeneratorLocalData localData, Reference<String> objectType, Reference<String> propertyType, Reference<Integer> propertyIndex, Reference<ValueKind> propertyValue) {
String objType = null;
String objSubType = null;
ValueKind propValue = null;
if(object != null){
GraphTargetItem oretType = object.returnType();
if(oretType instanceof UnresolvedAVM2Item){
@@ -194,6 +196,10 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
objType = abc.instance_info.get(c).getName(abc.constants).getNameWithNamespace(abc.constants);
propType = AVM2SourceGenerator.getTraitReturnType(abc, t).toString();
propIndex = t.name_index;
if(t instanceof TraitSlotConst){
TraitSlotConst tsc=(TraitSlotConst)t;
propValue = new ValueKind(tsc.value_index, tsc.value_kind);
}
break loopobjType;
}
}
@@ -202,6 +208,10 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
objType = abc.instance_info.get(c).getName(abc.constants).getNameWithNamespace(abc.constants);
propType = AVM2SourceGenerator.getTraitReturnType(abc, t).toString();
propIndex = t.name_index;
if(t instanceof TraitSlotConst){
TraitSlotConst tsc=(TraitSlotConst)t;
propValue = new ValueKind(tsc.value_index, tsc.value_kind);
}
break loopobjType;
}
}
@@ -222,14 +232,15 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> outPropNs = new Reference<>("");
Reference<Integer> outPropNsKind = new Reference<>(1);
Reference<String> outPropType = new Reference<>("");
if (AVM2SourceGenerator.searchPrototypeChain(false, abcs, nsname, n.getName(a.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType)) {
Reference<ValueKind> outPropValue = new Reference<>(null);
if (AVM2SourceGenerator.searchPrototypeChain(false, abcs, nsname, n.getName(a.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType, outPropValue)) {
objType = "".equals(outNs.getVal()) ? outName.getVal() : outNs.getVal() + "." + outName.getVal();
propType = outPropType.getVal();
propIndex = abc.constants.getMultinameId(new Multiname(Multiname.QNAME,
abc.constants.getStringId(propertyName, true),
abc.constants.getNamespaceId(new Namespace(outPropNsKind.getVal(), abc.constants.getStringId(outPropNs.getVal(), true)), 0, true), 0, 0, new ArrayList<Integer>()), true
);
propValue = outPropValue.getVal();
break loopobjType;
}
}
@@ -263,13 +274,15 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> outPropNs = new Reference<>("");
Reference<Integer> outPropNsKind = new Reference<>(1);
Reference<String> outPropType = new Reference<>("");
if (AVM2SourceGenerator.searchPrototypeChain(false, abcs, m.getNamespace(a.constants).getName(a.constants), m.getName(a.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType)) {
Reference<ValueKind> outPropValue = new Reference<>(null);
if (AVM2SourceGenerator.searchPrototypeChain(false, abcs, m.getNamespace(a.constants).getName(a.constants), m.getName(a.constants, new ArrayList<String>()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType,outPropValue)) {
objType = "".equals(outNs.getVal()) ? outName.getVal() : outNs.getVal() + "." + outName.getVal();
propType = outPropType.getVal();
propIndex = abc.constants.getMultinameId(new Multiname(Multiname.QNAME,
abc.constants.getStringId(propertyName, true),
abc.constants.getNamespaceId(new Namespace(outPropNsKind.getVal(), abc.constants.getStringId(outPropNs.getVal(), true)), 0, true), 0, 0, new ArrayList<Integer>()), true
);
propValue = outPropValue.getVal();
break loopa;
}
@@ -285,8 +298,10 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
allNsSet(), 0, new ArrayList<Integer>()), true);
propType = "*";
objType = "*";
propValue = null;
}
propertyValue.setVal(propValue);
propertyIndex.setVal(propIndex);
propertyType.setVal(propType);
objectType.setVal(objType);
@@ -296,7 +311,8 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> objType = new Reference<>("");
Reference<String> propType = new Reference<>("");
Reference<Integer> propIndex = new Reference<>(0);
resolve(localData, objType, propType, propIndex);
Reference<ValueKind> outPropValue = new Reference<>(null);
resolve(localData, objType, propType, propIndex, outPropValue);
return propIndex.getVal();
}
@@ -467,7 +483,8 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> objType = new Reference<>("");
Reference<String> propType = new Reference<>("");
Reference<Integer> propIndex = new Reference<>(0);
resolve(null, objType, propType, propIndex);
Reference<ValueKind> outPropValue = new Reference<>(null);
resolve(null, objType, propType, propIndex, outPropValue);
return new TypeItem(propType.getVal());
}
@@ -477,7 +494,8 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> objType = new Reference<>("");
Reference<String> propType = new Reference<>("");
Reference<Integer> propIndex = new Reference<>(0);
resolve(localData, objType, propType, propIndex);
Reference<ValueKind> outPropValue = new Reference<>(null);
resolve(localData, objType, propType, propIndex,outPropValue);
int propertyId = propIndex.getVal();
Object obj = resolveObject(localData, generator);
@@ -538,10 +556,11 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> outPropNs = new Reference<>("");
Reference<Integer> outPropNsKind = new Reference<>(1);
Reference<String> outPropType = new Reference<>("");
Reference<ValueKind> outPropValue = new Reference<>(null);
List<ABC> abcs = new ArrayList<>();
abcs.add(abc);
abcs.addAll(otherABCs);
if (cname != null && AVM2SourceGenerator.searchPrototypeChain(true, abcs, pkgName, cname, propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType)) {
if (cname != null && AVM2SourceGenerator.searchPrototypeChain(true, abcs, pkgName, cname, propertyName, outName, outNs, outPropNs, outPropNsKind, outPropType, outPropValue)) {
NameAVM2Item nobj = new NameAVM2Item(new TypeItem(localData.currentClass), 0, "this", null, false, openedNamespaces);
nobj.setRegNumber(0);
obj = nobj;
@@ -549,7 +568,8 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> objType = new Reference<>("");
Reference<String> propType = new Reference<>("");
Reference<Integer> propIndex = new Reference<>(0);
resolve(localData, objType, propType, propIndex);
Reference<ValueKind> propValue = new Reference<>(null);
resolve(localData, objType, propType, propIndex, outPropValue);
obj = ins(new FindPropertyStrictIns(), propIndex.getVal());
}
}
@@ -562,7 +582,8 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
Reference<String> objType = new Reference<>("");
Reference<String> propType = new Reference<>("");
Reference<Integer> propIndex = new Reference<>(0);
resolve(localData, objType, propType, propIndex);
Reference<ValueKind> outPropValue = new Reference<>(null);
resolve(localData, objType, propType, propIndex, outPropValue);
int propertyId = propIndex.getVal();
Object obj = resolveObject(localData, generator);

View File

@@ -25,8 +25,8 @@ import java.util.List;
*/
public class SetterAVM2Item extends MethodAVM2Item {
public SetterAVM2Item(boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
super(needsActivation, hasRest, line, override, isFinal, isStatic, namespace, methodName, paramTypes, paramNames, paramValues, body, subvariables, retType);
public SetterAVM2Item(String customNamespace,boolean needsActivation, boolean hasRest, int line, boolean override, boolean isFinal, boolean isStatic, int namespace, String methodName, List<GraphTargetItem> paramTypes, List<String> paramNames, List<GraphTargetItem> paramValues, List<GraphTargetItem> body, List<AssignableAVM2Item> subvariables, GraphTargetItem retType) {
super(customNamespace,needsActivation, hasRest, line, override, isFinal, isStatic, namespace, methodName, paramTypes, paramNames, paramValues, body, subvariables, retType);
}
}

View File

@@ -31,6 +31,7 @@ public class SlotAVM2Item extends AVM2Item {
private boolean isStatic;
public String var;
public GraphTargetItem type;
public String customNamespace;
public int getNamespace() {
return namespace;
@@ -40,13 +41,14 @@ public class SlotAVM2Item extends AVM2Item {
return isStatic;
}
public SlotAVM2Item(boolean isStatic, int namespace, String var, GraphTargetItem type, GraphTargetItem value) {
public SlotAVM2Item(String customNamespace, boolean isStatic, int namespace, String var, GraphTargetItem type, GraphTargetItem value) {
super(null, NOPRECEDENCE);
this.namespace = namespace;
this.value = value;
this.isStatic = isStatic;
this.var = var;
this.type = type;
this.customNamespace = customNamespace;
}
@Override

View File

@@ -1,5 +1,4 @@
TODO List for AS3 parser/compiler:
------------------------------
- E4X (XML)
- default xml namespace
- custom namespace modifiers
- default xml namespace