Merge pull request #42 from jindrapetrik/samenamespaces

Colliding trat/class names
This commit is contained in:
Jindra Petřík
2016-09-17 20:11:07 +02:00
committed by GitHub
103 changed files with 5048 additions and 4449 deletions
Binary file not shown.
@@ -166,6 +166,7 @@ ExceptionTarget = "exceptiontarget "{PositiveNumberLiteral}":"
"dispid" { yybegin(PARAMETERS); return new ParsedSymbol(ParsedSymbol.TYPE_KEYWORD_DISPID, yytext());}
"slotid" { yybegin(PARAMETERS); return new ParsedSymbol(ParsedSymbol.TYPE_KEYWORD_SLOTID, yytext());}
"value" { yybegin(PARAMETERS); return new ParsedSymbol(ParsedSymbol.TYPE_KEYWORD_VALUE, yytext());}
"type" { yybegin(PARAMETERS); return new ParsedSymbol(ParsedSymbol.TYPE_KEYWORD_TYPE, yytext());}
@@ -203,6 +203,8 @@ SingleCharacter = [^\r\n\'\\]
OIdentifierCharacter = [^\r\n\u00A7\\]
Preprocessor = \u00A7\u00A7 {Identifier}
NamespaceSuffix = "#" {DecIntegerLiteral}
RegExp = \/([^\r\n/]|\\\/)+\/[a-z]*
%state STRING, CHARLITERAL,XMLOPENTAG,XMLOPENTAGATTRIB,XMLINSTROPENTAG,XMLINSTRATTRIB,XMLCDATA,XMLCOMMENT,XML,OIDENTIFIER
@@ -371,6 +373,7 @@ RegExp = \/([^\r\n/]|\\\/)+\/[a-z]*
{Identifier} { return new ParsedSymbol(SymbolGroup.IDENTIFIER, SymbolType.IDENTIFIER, yytext()); }
/* regexp */
{RegExp} { return new ParsedSymbol(SymbolGroup.REGEXP, SymbolType.REGEXP, yytext()); }
{NamespaceSuffix} { return new ParsedSymbol(SymbolGroup.NAMESPACESUFFIX, SymbolType.NAMESPACESUFFIX, Integer.parseInt(yytext().substring(1))); }
}
<XMLOPENTAG> {
@@ -209,7 +209,7 @@ public class IdentifiersDeobfuscation {
}
public String deobfuscateNameWithPackage(boolean as3, String n, HashMap<DottedChain, DottedChain> namesMap, RenameType renameType, Map<DottedChain, DottedChain> selected) {
DottedChain nChain = DottedChain.parse(n);
DottedChain nChain = DottedChain.parseWithSuffix(n);
DottedChain pkg = nChain.getWithoutLast();
String name = nChain.getLast();
@@ -288,7 +288,7 @@ public class IdentifiersDeobfuscation {
usageType = "name";
}
DottedChain sChain = DottedChain.parse(s);
DottedChain sChain = DottedChain.parseWithSuffix(s);
if (selected != null) {
if (selected.containsKey(sChain)) {
return selected.get(sChain).toRawString();
@@ -314,14 +314,14 @@ public class IdentifiersDeobfuscation {
ret = fooString(firstUppercase, rndSize);
if (allVariableNamesStr.contains(ret)
|| isReservedWord(ret, as3)
|| namesMap.containsValue(DottedChain.parse(ret))) {
|| namesMap.containsValue(DottedChain.parseWithSuffix(ret))) {
found = true;
rndSize++;
}
}
} while (found);
namesMap.put(DottedChain.parse(s), DottedChain.parse(ret));
namesMap.put(DottedChain.parseWithSuffix(s), DottedChain.parseWithSuffix(ret));
return ret;
}
}
@@ -2204,7 +2204,7 @@ public final class SWF implements SWFContainerItem, Timelined {
public void renameAS2Identifier(String identifier, String newname) throws InterruptedException {
Map<DottedChain, DottedChain> selected = new HashMap<>();
selected.put(DottedChain.parse(identifier), DottedChain.parse(newname));
selected.put(DottedChain.parseWithSuffix(identifier), DottedChain.parseWithSuffix(newname));
renameAS2Identifiers(null, selected);
}
@@ -2276,7 +2276,7 @@ public final class SWF implements SWFContainerItem, Timelined {
String fname = dvf.toStringNoH(null);
String changed = deobfuscation.deobfuscateName(false, fname, false, "method", deobfuscated, renameType, selected);
if (changed != null) {
deobfuscated.put(DottedChain.parse(fname), DottedChain.parse(changed));
deobfuscated.put(DottedChain.parseWithSuffix(fname), DottedChain.parseWithSuffix(changed));
}
}
}
@@ -2295,7 +2295,7 @@ public final class SWF implements SWFContainerItem, Timelined {
String vname = dvf.toStringNoH(null);
String changed = deobfuscation.deobfuscateName(false, vname, false, "attribute", deobfuscated, renameType, selected);
if (changed != null) {
deobfuscated.put(DottedChain.parse(vname), DottedChain.parse(changed));
deobfuscated.put(DottedChain.parseWithSuffix(vname), DottedChain.parseWithSuffix(changed));
}
}
}
@@ -2331,7 +2331,7 @@ public final class SWF implements SWFContainerItem, Timelined {
changedNameStr = changedNameStr2;
}
ret++;
deobfuscated.put(DottedChain.parse(nameStr), DottedChain.parse(changedNameStr));
deobfuscated.put(DottedChain.parseWithSuffix(nameStr), DottedChain.parseWithSuffix(changedNameStr));
pos++;
}
name = mem.object;
@@ -2355,7 +2355,7 @@ public final class SWF implements SWFContainerItem, Timelined {
changedNameStr = changedNameStr2;
}
ret++;
deobfuscated.put(DottedChain.parse(nameStr), DottedChain.parse(changedNameStr));
deobfuscated.put(DottedChain.parseWithSuffix(nameStr), DottedChain.parseWithSuffix(changedNameStr));
pos++;
}
}
@@ -2899,7 +2899,8 @@ public final class SWF implements SWFContainerItem, Timelined {
timelined.setModified(true);
timelined.resetTimeline();
} else // timeline should be always the swf here
if (removeDependencies) {
{
if (removeDependencies) {
removeTagWithDependenciesFromTimeline(tag, timelined.getTimeline());
timelined.setModified(true);
} else {
@@ -2908,6 +2909,7 @@ public final class SWF implements SWFContainerItem, Timelined {
timelined.setModified(true);
}
}
}
}
@Override
@@ -3538,10 +3540,10 @@ public final class SWF implements SWFContainerItem, Timelined {
if (firstTrait instanceof TraitClass) {
int cindex = ((TraitClass) firstTrait).class_info;
Multiname superName = documentPack.abc.constants.getMultiname(documentPack.abc.instance_info.get(cindex).super_index);
String parentClass = superName.getNameWithNamespace(documentPack.abc.constants).toRawString();
String parentClass = superName.getNameWithNamespace(documentPack.abc.constants, true).toRawString();
if ("mx.managers.SystemManager".equals(parentClass)) {
for (Trait t : documentPack.abc.instance_info.get(cindex).instance_traits.traits) {
if ((t instanceof TraitMethodGetterSetter) && "info".equals(t.getName(documentPack.abc).getName(documentPack.abc.constants, new ArrayList<>(), true))) {
if ((t instanceof TraitMethodGetterSetter) && "info".equals(t.getName(documentPack.abc).getName(documentPack.abc.constants, new ArrayList<>(), true, true))) {
int mi = ((TraitMethodGetterSetter) t).method_info;
try {
@@ -3627,7 +3629,7 @@ public final class SWF implements SWFContainerItem, Timelined {
if (cit instanceof SetPropertyAVM2Item) {
if (cit.value instanceof GetLexAVM2Item) {
GetLexAVM2Item gl = (GetLexAVM2Item) cit.value;
ignoredClasses.add(gl.propertyName.getNameWithNamespace(p.abc.constants).toRawString());
ignoredClasses.add(gl.propertyName.getNameWithNamespace(p.abc.constants, true).toRawString());
}
}
}
@@ -50,7 +50,7 @@ public class SourceGeneratorLocalData implements Serializable {
public int finallyRegister = -1;
public String currentClass;
public String currentClass; //FIXME! Suffixed or not?
public String superClass = null;
@@ -79,7 +79,7 @@ public class SourceGeneratorLocalData implements Serializable {
public boolean isStatic = false;
public String getFullClass() {
return pkg == null ? currentClass : pkg.add(currentClass).toRawString();
return pkg == null ? currentClass : pkg.addWithSuffix(currentClass).toRawString();
}
public SourceGeneratorLocalData(HashMap<String, Integer> registerVars, Integer inFunction, Boolean inMethod, Integer forInLevel) {
@@ -42,6 +42,7 @@ import com.jpexs.decompiler.flash.abc.types.traits.TraitFunction;
import com.jpexs.decompiler.flash.abc.types.traits.TraitMethodGetterSetter;
import com.jpexs.decompiler.flash.abc.types.traits.TraitSlotConst;
import com.jpexs.decompiler.flash.abc.types.traits.Traits;
import com.jpexs.decompiler.flash.abc.usages.ClassNameInTraitMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.ClassNameMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.ConstVarNameMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.ConstVarTypeMultinameUsage;
@@ -53,6 +54,7 @@ import com.jpexs.decompiler.flash.abc.usages.MethodNameMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.MethodParamsMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.MethodReturnTypeMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.MultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.TraitMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.TypeNameMultinameUsage;
import com.jpexs.decompiler.flash.dumpview.DumpInfo;
import com.jpexs.decompiler.flash.dumpview.DumpInfoSpecial;
@@ -391,7 +393,7 @@ public class ABC {
int mIndex = body.getCode().code.get(ip).operands[0];
if (mIndex > 0) {
Multiname m = constants.getMultiname(mIndex);
if (m.getNameWithNamespace(constants).toRawString().equals("flash.utils.getDefinitionByName")) {
if (m.getNameWithNamespace(constants, true).toRawString().equals("flash.utils.getDefinitionByName")) {
if (ip > 0) {
if (body.getCode().code.get(ip - 1).definition instanceof PushStringIns) {
int strIndex = body.getCode().code.get(ip - 1).operands[0];
@@ -691,19 +693,9 @@ public class ABC {
SWFDecompilerPlugin.fireMethodBodyParsed(this, mb, swf);
}
refreshMultinameNamespaceSuffixes();
getMethodIndexing();
/*for(int i=0;i<script_count;i++){
MethodBody bod=bodies.get(bodyIdxFromMethodIdx.get(script_info.get(i).init_index));
GraphTextWriter t=new HighlightedTextWriter(Configuration.getCodeFormatting(),false);
try {
bod.toString("script", ScriptExportMode.PCODE, this, null, constants, method_info, t, new ArrayList<>());
} catch (InterruptedException ex) {
Logger.getLogger(ABC.class.getName()).log(Level.SEVERE, null, ex);
}
System.out.println(""+t.toString());
}
//System.exit(0);*/
SWFDecompilerPlugin.fireAbcParsed(this, swf);
}
@@ -836,9 +828,9 @@ public class ABC {
return getMethodIndexing().findMethodBodyIndex(methodInfo);
}
public MethodBody findBodyClassInitializerByClass(String className) {
public MethodBody findBodyClassInitializerByClass(String classNameWithSuffix) {
for (int i = 0; i < instance_info.size(); i++) {
if (className.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true))) {
if (classNameWithSuffix.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true, true))) {
MethodBody body = findBody(class_info.get(i).cinit_index);
if (body != null) {
return body;
@@ -849,9 +841,9 @@ public class ABC {
return null;
}
public MethodBody findBodyInstanceInitializerByClass(String className) {
public MethodBody findBodyInstanceInitializerByClass(String classNameWithSuffix) {
for (int i = 0; i < instance_info.size(); i++) {
if (className.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true))) {
if (classNameWithSuffix.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true, true))) {
MethodBody body = findBody(instance_info.get(i).iinit_index);
if (body != null) {
return body;
@@ -862,13 +854,13 @@ public class ABC {
return null;
}
public MethodBody findBodyByClassAndName(String className, String methodName) {
public MethodBody findBodyByClassAndName(String classNameWithSuffix, String methodNameWithSuffix) {
for (int i = 0; i < instance_info.size(); i++) {
if (className.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true))) {
if (classNameWithSuffix.equals(constants.getMultiname(instance_info.get(i).name_index).getName(constants, null, true, true))) {
for (Trait t : instance_info.get(i).instance_traits.traits) {
if (t instanceof TraitMethodGetterSetter) {
TraitMethodGetterSetter t2 = (TraitMethodGetterSetter) t;
if (methodName.equals(t2.getName(this).getName(constants, null, true))) {
if (methodNameWithSuffix.equals(t2.getName(this).getName(constants, null, true, true))) {
MethodBody body = findBody(t2.method_info);
if (body != null) {
return body;
@@ -880,7 +872,7 @@ public class ABC {
for (Trait t : class_info.get(i).static_traits.traits) {
if (t instanceof TraitMethodGetterSetter) {
TraitMethodGetterSetter t2 = (TraitMethodGetterSetter) t;
if (methodName.equals(t2.getName(this).getName(constants, null, true))) {
if (methodNameWithSuffix.equals(t2.getName(this).getName(constants, null, true, true))) {
MethodBody body = findBody(t2.method_info);
if (body != null) {
return body;
@@ -965,7 +957,7 @@ public class ABC {
TraitSlotConst s = ((TraitSlotConst) t);
if (s.isNamespace()) {
String key = constants.getNamespace(s.value_index).getName(constants).toRawString(); // assume not null
DottedChain val = constants.getMultiname(s.name_index).getNameWithNamespace(constants);
DottedChain val = constants.getMultiname(s.name_index).getNameWithNamespace(constants, true);
map.put(key, val);
}
}
@@ -1044,22 +1036,22 @@ public class ABC {
}
}
private void checkMultinameUsedInMethod(int multinameIndex, int methodInfo, List<MultinameUsage> ret, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
private void checkMultinameUsedInMethod(int multinameIndex, int methodInfo, List<MultinameUsage> ret, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
for (int p = 0; p < method_info.get(methodInfo).param_types.length; p++) {
if (method_info.get(methodInfo).param_types[p] == multinameIndex) {
ret.add(new MethodParamsMultinameUsage(this, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex));
ret.add(new MethodParamsMultinameUsage(this, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex));
break;
}
}
if (method_info.get(methodInfo).ret_type == multinameIndex) {
ret.add(new MethodReturnTypeMultinameUsage(this, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex));
ret.add(new MethodReturnTypeMultinameUsage(this, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex));
}
MethodBody body = findBody(methodInfo);
if (body != null) {
findMultinameUsageInTraits(body.traits, multinameIndex, isStatic, classIndex, ret, traitIndex);
findMultinameUsageInTraits(body.traits, multinameIndex, traitsType, scriptIndex, classIndex, ret, traitIndex);
for (ABCException e : body.exceptions) {
if ((e.name_index == multinameIndex) || (e.type_index == multinameIndex)) {
ret.add(new MethodBodyMultinameUsage(this, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex));
ret.add(new MethodBodyMultinameUsage(this, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex));
return;
}
}
@@ -1067,7 +1059,7 @@ public class ABC {
for (int o = 0; o < ins.definition.operands.length; o++) {
if (ins.definition.operands[o] == AVM2Code.DAT_MULTINAME_INDEX) {
if (ins.operands[o] == multinameIndex) {
ret.add(new MethodBodyMultinameUsage(this, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex));
ret.add(new MethodBodyMultinameUsage(this, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex));
return;
}
}
@@ -1076,23 +1068,30 @@ public class ABC {
}
}
private void findMultinameUsageInTraits(Traits traits, int multinameIndex, boolean isStatic, int classIndex, List<MultinameUsage> ret, int parentTraitIndex) {
private void findMultinameUsageInTraits(Traits traits, int multinameIndex, int traitsType, int scriptIndex, int classIndex, List<MultinameUsage> ret, int parentTraitIndex) {
for (int t = 0; t < traits.traits.size(); t++) {
//Assuming instance_info.name_index has same multiname as in the class trait
/*if (traits.traits.get(t) instanceof TraitClass) {
TraitClass tc = (TraitClass) traits.traits.get(t);
if (tc.name_index == multinameIndex) {
ret.add(new ClassNameInTraitMultinameUsage(this, multinameIndex, tc.class_info));
}
}*/
if (traits.traits.get(t) instanceof TraitSlotConst) {
TraitSlotConst tsc = (TraitSlotConst) traits.traits.get(t);
if (tsc.name_index == multinameIndex) {
ret.add(new ConstVarNameMultinameUsage(this, multinameIndex, classIndex, t, isStatic, traits, parentTraitIndex));
ret.add(new ConstVarNameMultinameUsage(this, multinameIndex, scriptIndex, classIndex, t, traitsType, traits, parentTraitIndex));
}
if (tsc.type_index == multinameIndex) {
ret.add(new ConstVarTypeMultinameUsage(this, multinameIndex, classIndex, t, isStatic, traits, parentTraitIndex));
ret.add(new ConstVarTypeMultinameUsage(this, multinameIndex, scriptIndex, classIndex, t, traitsType, traits, parentTraitIndex));
}
}
if (traits.traits.get(t) instanceof TraitMethodGetterSetter) {
TraitMethodGetterSetter tmgs = (TraitMethodGetterSetter) traits.traits.get(t);
if (tmgs.name_index == multinameIndex) {
ret.add(new MethodNameMultinameUsage(this, multinameIndex, classIndex, t, isStatic, false, traits, parentTraitIndex));
ret.add(new MethodNameMultinameUsage(this, multinameIndex, scriptIndex, classIndex, t, traitsType, false, traits, parentTraitIndex));
}
checkMultinameUsedInMethod(multinameIndex, tmgs.method_info, ret, classIndex, t, isStatic, false, traits, parentTraitIndex);
checkMultinameUsedInMethod(multinameIndex, tmgs.method_info, ret, scriptIndex, classIndex, t, traitsType, false, traits, parentTraitIndex);
}
}
}
@@ -1108,11 +1107,92 @@ public class ABC {
return ret;
}
public List<MultinameUsage> findMultinameUsageOfNamespace(int namespaceIndex) {
List<MultinameUsage> ret = new ArrayList<>();
for (int multinameIndex = 1; multinameIndex < constants.getMultinameCount(); multinameIndex++) {
if (constants.getMultiname(multinameIndex).namespace_index == namespaceIndex) {
ret.addAll(findMultinameUsage(multinameIndex));
}
}
return ret;
}
/**
* Gets colliding usages of multinames. For example same name
* consts/vars/methods or same class names. Mostly in obfuscated files.
*/
public Set<MultinameUsage> getCollidingMultinameUsages() {
//Reset
for (int multinameIndex = 1; multinameIndex < constants.getMultinameCount(); multinameIndex++) {
constants.getMultiname(multinameIndex).setDisplayNamespace(false);
}
//group qnames with same name
Map<String, List<Integer>> nameToQNameIndices = new HashMap<>();
for (int multinameIndex = 1; multinameIndex < constants.getMultinameCount(); multinameIndex++) {
Multiname m = constants.getMultiname(multinameIndex);
if (m.kind == Multiname.QNAME || m.kind == Multiname.QNAMEA) {
String name = m.getName(constants, new ArrayList<>(), true, false);
if (!nameToQNameIndices.containsKey(name)) {
nameToQNameIndices.put(name, new ArrayList<>());
}
nameToQNameIndices.get(name).add(multinameIndex);
}
}
Set<MultinameUsage> collidingUsages = new HashSet<>();
//find context of names with count 2 or more
for (String name : nameToQNameIndices.keySet()) {
List<Integer> multinameIndices = nameToQNameIndices.get(name);
if (multinameIndices.size() > 1) {
List<List<MultinameUsage>> allUsages = new ArrayList<>();
for (int multinameIndex : multinameIndices) {
List<MultinameUsage> usages = findMultinameUsage(multinameIndex);
for (MultinameUsage usage : usages) {
for (List<MultinameUsage> prevUsages : allUsages) {
for (MultinameUsage prevUsage : prevUsages) {
if (prevUsage.collides(usage)) {
collidingUsages.add(usage);
collidingUsages.add(prevUsage);
}
}
}
}
allUsages.add(usages);
}
}
}
return collidingUsages;
}
/**
* Appends namespace (#123) suffix to multinames which collide with each
* other. For example same name consts/vars/methods or same class names.
*/
public void refreshMultinameNamespaceSuffixes() {
Set<MultinameUsage> collidingMultinameUsages = getCollidingMultinameUsages();
Set<Integer> collidingMultinameIndices = new HashSet<>();
for (MultinameUsage col : collidingMultinameUsages) {
//System.err.println("collides " + col);
collidingMultinameIndices.add(col.multinameIndex);
}
for (int multinameIndex : collidingMultinameIndices) {
constants.getMultiname(multinameIndex).setDisplayNamespace(true);
}
}
public List<MultinameUsage> findMultinameUsage(int multinameIndex) {
List<MultinameUsage> ret = new ArrayList<>();
if (multinameIndex == 0) {
return ret;
}
for (int s = 0; s < script_info.size(); s++) {
findMultinameUsageInTraits(script_info.get(s).traits, multinameIndex, TraitMultinameUsage.TRAITS_TYPE_SCRIPT, s, -1, ret, -1);
}
for (int c = 0; c < instance_info.size(); c++) {
if (instance_info.get(c).name_index == multinameIndex) {
ret.add(new ClassNameMultinameUsage(this, multinameIndex, c));
@@ -1125,21 +1205,21 @@ public class ABC {
ret.add(new ImplementsMultinameUsage(this, multinameIndex, c));
}
}
checkMultinameUsedInMethod(multinameIndex, instance_info.get(c).iinit_index, ret, c, 0, false, true, null, -1);
checkMultinameUsedInMethod(multinameIndex, class_info.get(c).cinit_index, ret, c, 0, true, true, null, -1);
findMultinameUsageInTraits(instance_info.get(c).instance_traits, multinameIndex, false, c, ret, -1);
findMultinameUsageInTraits(class_info.get(c).static_traits, multinameIndex, true, c, ret, -1);
checkMultinameUsedInMethod(multinameIndex, instance_info.get(c).iinit_index, ret, -1/*FIXME*/, c, 0, TraitMultinameUsage.TRAITS_TYPE_INSTANCE, true, null, -1);
checkMultinameUsedInMethod(multinameIndex, class_info.get(c).cinit_index, ret, -1/*FIXME*/, c, 0, TraitMultinameUsage.TRAITS_TYPE_CLASS, true, null, -1);
findMultinameUsageInTraits(instance_info.get(c).instance_traits, multinameIndex, TraitMultinameUsage.TRAITS_TYPE_INSTANCE, -1/*FIXME*/, c, ret, -1);
findMultinameUsageInTraits(class_info.get(c).static_traits, multinameIndex, TraitMultinameUsage.TRAITS_TYPE_CLASS, -1/*FIXME*/, c, ret, -1);
}
loopm:
for (int m = 1; m < constants.getMultinameCount(); m++) {
if (constants.getMultiname(m).kind == Multiname.TYPENAME) {
if (constants.getMultiname(m).qname_index == multinameIndex) {
ret.add(new TypeNameMultinameUsage(this, m));
for (int t = 1; t < constants.getMultinameCount(); t++) {
if (constants.getMultiname(t).kind == Multiname.TYPENAME) {
if (constants.getMultiname(t).qname_index == multinameIndex) {
ret.add(new TypeNameMultinameUsage(this, multinameIndex, t));
continue;
}
for (int mp : constants.getMultiname(m).params) {
for (int mp : constants.getMultiname(t).params) {
if (mp == multinameIndex) {
ret.add(new TypeNameMultinameUsage(this, m));
ret.add(new TypeNameMultinameUsage(this, multinameIndex, t));
continue loopm;
}
}
@@ -1148,11 +1228,11 @@ public class ABC {
return ret;
}
public int findMethodInfoByName(int classId, String methodName) {
public int findMethodInfoByName(int classId, String methodNameWithSuffix) {
if (classId > -1) {
for (Trait t : instance_info.get(classId).instance_traits.traits) {
if (t instanceof TraitMethodGetterSetter) {
if (t.getName(this).getName(constants, null, true).equals(methodName)) {
if (t.getName(this).getName(constants, null, true, true).equals(methodNameWithSuffix)) {
return ((TraitMethodGetterSetter) t).method_info;
}
}
@@ -1161,11 +1241,11 @@ public class ABC {
return -1;
}
public int findMethodBodyByName(int classId, String methodName) {
public int findMethodBodyByName(int classId, String methodNameWithSuffix) {
if (classId > -1) {
for (Trait t : instance_info.get(classId).instance_traits.traits) {
if (t instanceof TraitMethodGetterSetter) {
if (t.getName(this).getName(constants, null, true).equals(methodName)) {
if (t.getName(this).getName(constants, null, true, true).equals(methodNameWithSuffix)) {
return findBodyIndex(((TraitMethodGetterSetter) t).method_info);
}
}
@@ -1184,10 +1264,10 @@ public class ABC {
return findClassByName(str);
}
public int findClassByName(String name) {
public int findClassByName(String nameWithSuffix) {
for (int c = 0; c < instance_info.size(); c++) {
DottedChain s = constants.getMultiname(instance_info.get(c).name_index).getNameWithNamespace(constants);
if (name.equals(s.toRawString())) {
DottedChain s = constants.getMultiname(instance_info.get(c).name_index).getNameWithNamespace(constants, true);
if (nameWithSuffix.equals(s.toRawString())) {
return c;
}
}
@@ -29,30 +29,37 @@ public class ClassPath {
public final String className;
public ClassPath(DottedChain packageStr, String className) {
public final String namespaceSuffix;
public ClassPath(DottedChain packageStr, String className, String namespaceSuffix) {
this.packageStr = packageStr == null ? DottedChain.TOPLEVEL : packageStr;
this.className = className;
this.namespaceSuffix = namespaceSuffix;
}
@Override
public String toString() {
return packageStr.add(className).toPrintableString(true);
return packageStr.add(className, namespaceSuffix).toPrintableString(true);
}
public String toRawString() {
return packageStr.add(className).toRawString();
return packageStr.add(className, namespaceSuffix).toRawString();
}
@Override
public int hashCode() {
int hash = 7;
hash = 37 * hash + Objects.hashCode(packageStr);
hash = 37 * hash + Objects.hashCode(className);
int hash = 3;
hash = 31 * hash + Objects.hashCode(this.packageStr);
hash = 31 * hash + Objects.hashCode(this.className);
hash = 31 * hash + Objects.hashCode(this.namespaceSuffix);
return hash;
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
@@ -60,9 +67,16 @@ public class ClassPath {
return false;
}
final ClassPath other = (ClassPath) obj;
if (!Objects.equals(packageStr, other.packageStr)) {
if (!Objects.equals(this.className, other.className)) {
return false;
}
return Objects.equals(className, other.className);
if (!Objects.equals(this.namespaceSuffix, other.namespaceSuffix)) {
return false;
}
if (!Objects.equals(this.packageStr, other.packageStr)) {
return false;
}
return true;
}
}
@@ -98,7 +98,7 @@ public class ScriptPack extends AS3ClassTreeItem {
}
public ScriptPack(ClassPath path, ABC abc, List<ABC> allAbcs, int scriptIndex, List<Integer> traitIndices) {
super(path.className, path);
super(path.className, path.namespaceSuffix, path);
this.abc = abc;
this.scriptIndex = scriptIndex;
this.traitIndices = traitIndices;
@@ -124,7 +124,7 @@ public class ScriptPack extends AS3ClassTreeItem {
Multiname name = abc.script_info.get(scriptIndex).traits.traits.get(t).getName(abc);
Namespace ns = name.getNamespace(abc.constants);
if ((ns.kind == Namespace.KIND_PACKAGE) || (ns.kind == Namespace.KIND_PACKAGE_INTERNAL)) {
scriptName = name.getName(abc.constants, null, false);
scriptName = name.getName(abc.constants, null, false, true);
}
}
return scriptName;
@@ -1754,7 +1754,7 @@ public class AVM2Code implements Cloneable {
if (code.get(ip + plus + 2).definition instanceof SwapIns) {
if (code.get(ip + plus + 4).definition instanceof PopScopeIns) {
if (code.get(ip + plus + 3).definition instanceof SetPropertyIns) {
functionName = abc.constants.getMultiname(code.get(ip + plus + 3).operands[0]).getName(abc.constants, fullyQualifiedNames, true);
functionName = abc.constants.getMultiname(code.get(ip + plus + 3).operands[0]).getName(abc.constants, fullyQualifiedNames, true, true);
scopeStack.pop();// with
output.remove(output.size() - 1); // with
ip = ip + plus + 4; // +1 below
@@ -2040,7 +2040,7 @@ public class AVM2Code implements Cloneable {
if (value instanceof NewFunctionAVM2Item) {
NewFunctionAVM2Item f = (NewFunctionAVM2Item) value;
f.functionName = tsc.getName(abc).getName(abc.constants, fullyQualifiedNames, true);
f.functionName = tsc.getName(abc).getName(abc.constants, fullyQualifiedNames, true, true);
}
AssignedValue av = new AssignedValue(value, initializerType, methodIndex);
convertData.assignedValues.put(tsc, av);
@@ -2085,7 +2085,7 @@ public class AVM2Code implements Cloneable {
if (param_types[i] == 0) {
type = TypeItem.UNBOUNDED;
} else {
type = new TypeItem(abc.constants.getMultiname(param_types[i]).getNameWithNamespace(abc.constants));
type = new TypeItem(abc.constants.getMultiname(param_types[i]).getNameWithNamespace(abc.constants, true));
}
if (d.length > r) {
d[r] = new DeclarationAVM2Item(new SetLocalAVM2Item(null, null, r, new NullAVM2Item(null, null)), type);
@@ -2174,8 +2174,7 @@ public class AVM2Code implements Cloneable {
ins.operands[j] = updater.updateOperandOffset(target, ins.operands[j]);
}
}*/ //Faster, but not so universal
{
if (ins.definition instanceof IfTypeIns) {
if (ins.definition instanceof IfTypeIns) {
long target = ins.getTargetAddress();
try {
ins.operands[0] = updater.updateOperandOffset(ins.getAddress(), target, ins.operands[0]);
@@ -2183,7 +2182,6 @@ public class AVM2Code implements Cloneable {
throw new ConvertException("Invalid offset (" + ins + ")", i);
}
}
}
ins.setAddress(updater.updateInstructionOffset(ins.getAddress()));
//Note: changing operands here does not change instruction byte length as offsets are always S24 (not variable length)
}
@@ -34,8 +34,10 @@ import com.jpexs.helpers.HashArrayList;
import com.jpexs.helpers.utf8.Utf8PrintWriter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;
@@ -662,7 +664,7 @@ public class AVM2ConstantPool implements Cloneable {
String str = getString(index);
DottedChain chain = dottedChainCache.get(str);
if (chain == null) {
chain = DottedChain.parse(str);
chain = DottedChain.parseWithSuffix(str);
dottedChainCache.put(str, chain);
}
@@ -48,9 +48,9 @@ public class AVM2Deobfuscation {
private final Map<String, Integer> usageTypesCount = new HashMap<>();
public static final DottedChain FLASH_PROXY = new DottedChain("flash", "utils", "flash_proxy");
public static final DottedChain FLASH_PROXY = new DottedChain(new String[]{"flash", "utils", "flash_proxy"}, "");
public static final DottedChain BUILTIN = new DottedChain("-");
public static final DottedChain BUILTIN = new DottedChain(new String[]{"-"}, "");
public AVM2Deobfuscation(SWF swf, AVM2ConstantPool constants) {
this.swf = swf;
@@ -111,12 +111,12 @@ public class AVM2Deobfuscation {
}
if (swf.as3StringConstantExists(ret)
|| IdentifiersDeobfuscation.isReservedWord2(ret)
|| deobfuscated.containsValue(DottedChain.parse(ret))) {
|| deobfuscated.containsValue(DottedChain.parseWithSuffix(ret))) {
found = true;
rndSize++;
}
} while (found);
deobfuscated.put(DottedChain.parse(orig), DottedChain.parse(ret));
deobfuscated.put(DottedChain.parseWithSuffix(orig), DottedChain.parseWithSuffix(ret));
return ret;
}
@@ -130,7 +130,7 @@ public class AVM2Deobfuscation {
}
boolean isValid = isValidNSPart(s);
if (!isValid) {
DottedChain sChain = DottedChain.parse(s);
DottedChain sChain = DottedChain.parseWithSuffix(s);
DottedChain newName;
if (namesMap.containsKey(sChain)) {
newName = namesMap.get(sChain);
@@ -186,19 +186,19 @@ public class AVM2Deobfuscation {
if (!isValid) {
DottedChain newname;
DottedChain sChain = DottedChain.parse(s);
DottedChain sChain = DottedChain.parseWithSuffix(s);
if (namesMap.containsKey(sChain)) {
newname = namesMap.get(sChain);
} else {
String str = fooString(namesMap, constants.getString(strIndex), firstUppercase, stringUsageTypes.get(strIndex), renameType);
newname = DottedChain.parse(str);
newname = DottedChain.parseWithSuffix(str);
}
if (stringUsages.contains(strIndex) || namespaceUsages.contains(strIndex)) { // this name is already referenced as String
strIndex = constants.addString(s); // add new index
}
constants.setString(strIndex, newname.toRawString());
if (!namesMap.containsKey(sChain)) {
namesMap.put(sChain, DottedChain.parse(constants.getString(strIndex)));
namesMap.put(sChain, DottedChain.parseWithSuffix(constants.getString(strIndex)));
}
}
return strIndex;
@@ -0,0 +1,100 @@
/*
* Copyright (C) 2010-2016 JPEXS, All rights reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3.0 of the License, or (at your option) any later version.
*
* This library 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library.
*/
package com.jpexs.decompiler.flash.abc.avm2.deobfuscation;
import com.jpexs.decompiler.flash.SWF;
import com.jpexs.decompiler.flash.abc.ABC;
import com.jpexs.decompiler.flash.abc.types.Multiname;
import com.jpexs.decompiler.flash.abc.types.NamespaceSet;
import com.jpexs.decompiler.flash.abc.usages.MultinameUsage;
import com.jpexs.decompiler.flash.tags.ABCContainerTag;
import com.jpexs.decompiler.flash.tags.Tag;
import java.util.HashSet;
import java.util.Objects;
import java.util.Set;
public class AbcMultiNameCollisionFixer {
public int fixCollisions(SWF swf) {
int ret = 0;
for (ABCContainerTag tag : swf.getAbcList()) {
ret += this.fixCollisions(tag.getABC());
}
return ret;
}
public int fixCollisions(ABC abc) {
Set<MultinameUsage> collidingUsages = abc.getCollidingMultinameUsages();
Set<Integer> collidingMultinameIndices = new HashSet<>();
for (MultinameUsage usage : collidingUsages) {
collidingMultinameIndices.add(usage.getMultinameIndex());
}
Set<String> newNames = new HashSet<>();
int ret = 0;
for (int multiNameIndex : collidingMultinameIndices) {
Multiname multiName = abc.constants.getMultiname(multiNameIndex);
int namespace = multiName.namespace_index;
String oldName = abc.constants.getString(multiName.name_index);
String selectedBaseName = oldName + "_" + multiName.namespace_index;
String selectedName = selectedBaseName;
int cnt = 0;
while (!newNames.contains(selectedName) && abc.constants.getStringId(selectedName, false) > -1) { //already exists such name, but was not added during this collisionFixes
cnt++;
selectedName = selectedBaseName + "_" + cnt;
}
newNames.add(selectedName);
int newNameIndex = abc.constants.getStringId(selectedName, true);
multiName.name_index = newNameIndex;
//Find other names with same name and namespace which are not listed as colliding, but are related
for (int m = 1; m < abc.constants.getMultinameCount(); m++) {
if (collidingMultinameIndices.contains(m)) {
continue;
}
Multiname other = abc.constants.getMultiname(m);
if (other.hasOwnName() && other.hasOwnNamespace()) {
int otherNamespace = other.namespace_index;
if (namespace == otherNamespace) {
if (Objects.equals(oldName, abc.constants.getString(other.name_index))) {
other.name_index = newNameIndex;
ret++;
}
}
} else if (other.hasOwnName() && other.hasOwnNamespaceSet()) {
NamespaceSet otherNamespaceSet = abc.constants.getNamespaceSet(other.namespace_set_index);
//NamespaceSet with only one namespace - this one
if (otherNamespaceSet.namespaces.length == 1) {
int otherNamespace = otherNamespaceSet.namespaces[0];
if (namespace == otherNamespace) {
if (Objects.equals(oldName, abc.constants.getString(other.name_index))) {
other.name_index = newNameIndex;
ret++;
}
}
}
//What if there are more namespaces in the set and how about runtime resolved names?
}
}
ret++;
}
if (ret > 0) {
((Tag) abc.parentTag).setModified(true);
}
return ret;
}
}
@@ -214,7 +214,7 @@ public abstract class InstructionDefinition implements Serializable {
}
}
return new FullMultinameAVM2Item(property, ins, localData.lineStartInstruction, multinameIndex, localData.abc.constants.getMultiname(multinameIndex).getName(localData.getConstants(), new ArrayList<>(), true), name, ns);
return new FullMultinameAVM2Item(property, ins, localData.lineStartInstruction, multinameIndex, localData.abc.constants.getMultiname(multinameIndex).getName(localData.getConstants(), new ArrayList<>(), true, true), name, ns);
}
protected int getMultinameRequiredStackSize(AVM2ConstantPool constants, int multinameIndex) {
@@ -258,7 +258,7 @@ public abstract class InstructionDefinition implements Serializable {
if (constants.getMultiname(multinameIndex).needsName()) {
name = stack.get(pos).toString();
} else {
name = GraphTextWriter.hilighOffset(constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, false), ins.getAddress());
name = GraphTextWriter.hilighOffset(constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, false, true), ins.getAddress());
}
return name + ns;
}
@@ -24,5 +24,5 @@ import com.jpexs.decompiler.graph.DottedChain;
*/
public interface AlchemyTypeIns {
public static final DottedChain ALCHEMY_PACKAGE = new DottedChain("avm2", "intrinsics", "memory");
public static final DottedChain ALCHEMY_PACKAGE = new DottedChain(new String[]{"avm2", "intrinsics", "memory"}, DottedChain.NO_SUFFIX);
}
@@ -101,7 +101,7 @@ public class ConstructIns extends InstructionDefinition {
}
if (obj instanceof GetLexAVM2Item) {
GetLexAVM2Item glt = (GetLexAVM2Item) obj;
isXML = glt.propertyName.getName(localData.getConstants(), localData.fullyQualifiedNames, true).equals("XML");
isXML = glt.propertyName.getName(localData.getConstants(), localData.fullyQualifiedNames, true, true).equals("XML");
}
if (isXML) {
@@ -129,7 +129,7 @@ public class ConstructIns extends InstructionDefinition {
}
if (obj instanceof GetLexAVM2Item) {
GetLexAVM2Item glt = (GetLexAVM2Item) obj;
isRegExp = glt.propertyName.getName(localData.getConstants(), localData.fullyQualifiedNames, true).equals("RegExp");
isRegExp = glt.propertyName.getName(localData.getConstants(), localData.fullyQualifiedNames, true, true).equals("RegExp");
}
if (isRegExp && (args.size() >= 1) && (args.get(0) instanceof StringAVM2Item) && (args.size() == 1 || (args.size() == 2 && args.get(1) instanceof StringAVM2Item))) {
@@ -46,7 +46,7 @@ public class NewClassIns extends InstructionDefinition {
stack.pop().toString(writer, LocalData.create(localData.getConstants(), localData.localRegNames, localData.fullyQualifiedNames));
String baseType = writer.toString();
ABC abc = localData.abc;
stack.push(new UnparsedAVM2Item(ins, localData.lineStartInstruction, "new " + abc.constants.getMultiname(abc.instance_info.get(clsIndex).name_index).getName(localData.getConstants(), localData.fullyQualifiedNames, false) + ".class extends " + baseType));
stack.push(new UnparsedAVM2Item(ins, localData.lineStartInstruction, "new " + abc.constants.getMultiname(abc.instance_info.get(clsIndex).name_index).getName(localData.getConstants(), localData.fullyQualifiedNames, false, true) + ".class extends " + baseType));
}
@Override
@@ -68,7 +68,7 @@ public abstract class GetLocalTypeIns extends InstructionDefinition {
List<Trait> ts = localData.getInstanceInfo().get(localData.classIndex).instance_traits.traits;
boolean isBasicObject = localData.thisHasDefaultToPrimitive;
Multiname m = localData.getInstanceInfo().get(localData.classIndex).getName(localData.getConstants());
stack.push(new ThisAVM2Item(ins, localData.lineStartInstruction, m, m.getNameWithNamespace(localData.getConstants()), isBasicObject));
stack.push(new ThisAVM2Item(ins, localData.lineStartInstruction, m, m.getNameWithNamespace(localData.getConstants(), true), isBasicObject));
}
return;
}
@@ -104,7 +104,7 @@ public class SetSlotIns extends InstructionDefinition implements SetTypeIns {
if (slotname != null) {
if (value instanceof LocalRegAVM2Item) {
LocalRegAVM2Item lr = (LocalRegAVM2Item) value;
String slotNameStr = slotname.getName(localData.getConstants(), localData.fullyQualifiedNames, true);
String slotNameStr = slotname.getName(localData.getConstants(), localData.fullyQualifiedNames, true, true);
if (localData.localRegNames.containsKey(lr.regIndex)) {
if (localData.localRegNames.get(lr.regIndex).equals(slotNameStr)) {
return; //Register with same name to slot
@@ -179,7 +179,7 @@ public class SetSlotIns extends InstructionDefinition implements SetTypeIns {
for (int t = 0; t < body.traits.traits.size(); t++) {
if (body.traits.traits.get(t) instanceof TraitSlotConst) {
if (((TraitSlotConst) body.traits.traits.get(t)).slot_id == slotIndex) {
slotname = body.traits.traits.get(t).getName(abc).getName(abc.constants, fullyQualifiedNames, true);
slotname = body.traits.traits.get(t).getName(abc).getName(abc.constants, fullyQualifiedNames, true, true);
}
}
@@ -56,7 +56,7 @@ public class AsTypeIns extends InstructionDefinition {
public void translate(AVM2LocalData localData, TranslateStack stack, AVM2Instruction ins, List<GraphTargetItem> output, String path) {
GraphTargetItem val = stack.pop();
stack.push(new AsTypeAVM2Item(ins, localData.lineStartInstruction, val, new FullMultinameAVM2Item(false, ins, localData.lineStartInstruction, ins.operands[0], localData.abc.constants.getMultiname(ins.operands[0]).getName(localData.getConstants(), new ArrayList<>(), true))));
stack.push(new AsTypeAVM2Item(ins, localData.lineStartInstruction, val, new FullMultinameAVM2Item(false, ins, localData.lineStartInstruction, ins.operands[0], localData.abc.constants.getMultiname(ins.operands[0]).getName(localData.getConstants(), new ArrayList<>(), true, true))));
}
@Override
@@ -42,7 +42,7 @@ public class IsTypeIns extends InstructionDefinition {
public void translate(AVM2LocalData localData, TranslateStack stack, AVM2Instruction ins, List<GraphTargetItem> output, String path) {
int multinameIndex = ins.operands[0];
GraphTargetItem value = stack.pop();
stack.push(new IsTypeAVM2Item(ins, localData.lineStartInstruction, value, new FullMultinameAVM2Item(false, ins, localData.lineStartInstruction, multinameIndex, localData.abc.constants.getMultiname(multinameIndex).getName(localData.getConstants(), new ArrayList<>(), true))));
stack.push(new IsTypeAVM2Item(ins, localData.lineStartInstruction, value, new FullMultinameAVM2Item(false, ins, localData.lineStartInstruction, multinameIndex, localData.abc.constants.getMultiname(multinameIndex).getName(localData.getConstants(), new ArrayList<>(), true, true))));
}
@Override
@@ -37,7 +37,7 @@ public class ClassAVM2Item extends AVM2Item {
@Override
public GraphTextWriter appendTo(GraphTextWriter writer, LocalData localData) {
return writer.append(className.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false));
return writer.append(className.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true));
}
@Override
@@ -80,7 +80,7 @@ public class FullMultinameAVM2Item extends AVM2Item {
if (name != null) {
cname = name.toString(LocalData.create(constants, localRegNames, fullyQualifiedNames));
} else {
cname = (constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, true));
cname = (constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, true, true));
}
String cns = "";
if (namespace != null) {
@@ -121,7 +121,7 @@ public class FullMultinameAVM2Item extends AVM2Item {
AVM2ConstantPool constants = localData.constantsAvm2;
List<DottedChain> fullyQualifiedNames = property ? new ArrayList<>() : localData.fullyQualifiedNames;
if (multinameIndex > 0 && multinameIndex < constants.getMultinameCount()) {
writer.append(constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, false));
writer.append(constants.getMultiname(multinameIndex).getName(constants, fullyQualifiedNames, false, true));
} else {
writer.append("§§multiname(").append(multinameIndex).append(")");
}
@@ -38,7 +38,7 @@ public class GetLexAVM2Item extends AVM2Item {
public GetLexAVM2Item(GraphSourceItem instruction, GraphSourceItem lineStartIns, Multiname propertyName, AVM2ConstantPool constants) {
super(instruction, lineStartIns, PRECEDENCE_PRIMARY);
this.propertyName = propertyName;
this.fullPropertyName = propertyName.getNameWithNamespace(constants);
this.fullPropertyName = propertyName.getNameWithNamespace(constants, true);
}
public String getRawPropertyName() {
@@ -47,9 +47,9 @@ public class GetLexAVM2Item extends AVM2Item {
@Override
public GraphTextWriter appendTo(GraphTextWriter writer, LocalData localData) {
String localName = propertyName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false);
String localName = propertyName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true);
getSrcData().localName = localName;
return writer.append(propertyName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false));
return writer.append(propertyName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true));
}
@Override
@@ -46,18 +46,18 @@ public class GetSlotAVM2Item extends AVM2Item {
}
getSrcData().localName = getNameAsStr(localData);
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false));
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true));
}
public String getNameAsStr(LocalData localData) {
return slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false);
return slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true);
}
public GraphTextWriter getName(GraphTextWriter writer, LocalData localData) {
if (slotName == null) {
return writer.append("/*UnknownSlot*/");
}
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false));
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true));
}
@Override
@@ -42,17 +42,17 @@ import java.util.List;
*/
public class InitVectorAVM2Item extends AVM2Item {
public static final DottedChain VECTOR_PACKAGE = new DottedChain("__AS3__", "vec");
public static final DottedChain VECTOR_PACKAGE = new DottedChain(new String[]{"__AS3__", "vec"}, "");
public static final DottedChain VECTOR_FQN = new DottedChain("__AS3__", "vec", "Vector");
public static final DottedChain VECTOR_FQN = new DottedChain(new String[]{"__AS3__", "vec", "Vector"}, "");
public static final DottedChain VECTOR_INT = new DottedChain("__AS3__", "vec", "Vector$int");
public static final DottedChain VECTOR_INT = new DottedChain(new String[]{"__AS3__", "vec", "Vector$int"}, "");
public static final DottedChain VECTOR_DOUBLE = new DottedChain("__AS3__", "vec", "Vector$double");
public static final DottedChain VECTOR_DOUBLE = new DottedChain(new String[]{"__AS3__", "vec", "Vector$double"}, "");
public static final DottedChain VECTOR_UINT = new DottedChain("__AS3__", "vec", "Vector$uint");
public static final DottedChain VECTOR_UINT = new DottedChain(new String[]{"__AS3__", "vec", "Vector$uint"}, "");
public static final DottedChain VECTOR_OBJECT = new DottedChain("__AS3__", "vec", "Vector$object");
public static final DottedChain VECTOR_OBJECT = new DottedChain(new String[]{"__AS3__", "vec", "Vector$object"}, "");
public GraphTargetItem subtype;
@@ -61,7 +61,7 @@ public class SetSlotAVM2Item extends AVM2Item implements SetTypeAVM2Item, Assign
@Override
public GraphTextWriter appendTo(GraphTextWriter writer, LocalData localData) throws InterruptedException {
getSrcData().localName = slotName == null ? "/*UnknownSlot*/" : slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false);
getSrcData().localName = slotName == null ? "/*UnknownSlot*/" : slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true);
if (getSrcData().localName.equals(value.toString(localData))) {
//assigning parameters to activation reg
return writer;
@@ -75,14 +75,14 @@ public class SetSlotAVM2Item extends AVM2Item implements SetTypeAVM2Item, Assign
}
public String getNameAsStr(LocalData localData) {
return slotName == null ? "/*UnknownSlot*/" : slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false);
return slotName == null ? "/*UnknownSlot*/" : slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true);
}
public GraphTextWriter getName(GraphTextWriter writer, LocalData localData) {
if (slotName == null) {
return writer.append("/*UnknownSlot*/");
}
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false));
return writer.append(slotName.getName(localData.constantsAvm2, localData.fullyQualifiedNames, false, true));
}
@Override
@@ -97,7 +97,7 @@ public class TryAVM2Item extends AVM2Item implements Block {
int eti = catchExceptions.get(e).type_index;
data.declaredType = eti <= 0 ? DottedChain.ALL : localData.constantsAvm2.getMultiname(eti).getNameWithNamespace(localData.constantsAvm2);
data.declaredType = eti <= 0 ? DottedChain.ALL : localData.constantsAvm2.getMultiname(eti).getNameWithNamespace(localData.constantsAvm2, true);
writer.hilightSpecial(localName, HighlightSpecialType.TRY_NAME, e, data);
writer.append(":");
writer.hilightSpecial(catchExceptions.get(e).getTypeName(localData.constantsAvm2, localData.fullyQualifiedNames), HighlightSpecialType.TRY_TYPE, e);
@@ -1129,6 +1129,7 @@ public class ASM3Parser {
info.optional[i] = optional.get(i);
}
}
abc.refreshMultinameNamespaceSuffixes();
return code;
}
}
File diff suppressed because it is too large Load Diff
@@ -1244,7 +1244,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
if (t instanceof TraitSlotConst) {
TraitSlotConst tsc = (TraitSlotConst) t;
if (tsc.kindType == Trait.TRAIT_SLOT) {
if ("_skinParts".equals(tsc.getName(ci.abc).getName(ci.abc.constants, new ArrayList<>(), true))) {
if ("_skinParts".equals(tsc.getName(ci.abc).getName(ci.abc.constants, new ArrayList<>(), true, true))) {
if (d.assignedValues.containsKey(tsc)) {
if (d.assignedValues.get(tsc).value instanceof NewObjectAVM2Item) {
NewObjectAVM2Item no = (NewObjectAVM2Item) d.assignedValues.get(tsc).value;
@@ -1270,7 +1270,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
}
*/
List<GraphTargetItem> getterBody = new ArrayList<>();
UnresolvedAVM2Item sp = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, false, TypeItem.UNBOUNDED, 0, new DottedChain("_skinParts"),
UnresolvedAVM2Item sp = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, false, TypeItem.UNBOUNDED, 0, new DottedChain(new String[]{"_skinParts"}, ""),
null, openedNamespaces);
getterBody.add(new ReturnValueAVM2Item(null, null, sp));
List<AssignableAVM2Item> subvars = new ArrayList<>();
@@ -1577,7 +1577,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
List<Integer> registerLines = new ArrayList<>();
List<String> registerTypes = new ArrayList<>();
if (className != null) {
String fullClassName = pkg.add(className).toRawString();
String fullClassName = pkg.addWithSuffix(className).toRawString();
registerTypes.add(fullClassName);
localData.scopeStack.add(new LocalRegAVM2Item(null, null, registerNames.size(), null));
registerNames.add("this");
@@ -1831,9 +1831,9 @@ public class AVM2SourceGenerator implements SourceGenerator {
TraitSlotConst tsc = (TraitSlotConst) mbody.traits.traits.get(i);
GraphTargetItem type = TypeItem.UNBOUNDED;
if (tsc.type_index > 0) {
type = new TypeItem(abcIndex.getSelectedAbc().constants.getMultiname(tsc.type_index).getNameWithNamespace(abcIndex.getSelectedAbc().constants));
type = new TypeItem(abcIndex.getSelectedAbc().constants.getMultiname(tsc.type_index).getNameWithNamespace(abcIndex.getSelectedAbc().constants, true));
}
NameAVM2Item d = new NameAVM2Item(type, 0, tsc.getName(abcIndex.getSelectedAbc()).getName(abcIndex.getSelectedAbc().constants, null, true), NameAVM2Item.getDefaultValue("" + type), true, new ArrayList<>());
NameAVM2Item d = new NameAVM2Item(type, 0, tsc.getName(abcIndex.getSelectedAbc()).getName(abcIndex.getSelectedAbc().constants, null, true, true), NameAVM2Item.getDefaultValue("" + type), true, new ArrayList<>());
d.setSlotNumber(tsc.slot_id);
d.setSlotScope(slotScope);
mbodyCode.addAll(0, toInsList(d.toSourceIgnoreReturnValue(localData, this)));
@@ -2452,7 +2452,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
indices.add(
abc.getSelectedAbc().constants.getMultinameId(
Multiname.createQName(false,
abc.getSelectedAbc().constants.getStringId(superName.getName(a.constants, null, true), true),
abc.getSelectedAbc().constants.getStringId(superName.getName(a.constants, null, true, true /*FIXME!!! ???*/), true),
abc.getSelectedAbc().constants.getNamespaceId(superName.getNamespace(a.constants).kind, superName.getNamespace(a.constants).getName(a.constants), 0, true)), true)
);
}
@@ -2503,9 +2503,9 @@ public class AVM2SourceGenerator implements SourceGenerator {
private static boolean searchPrototypeChain(int selectedNs, boolean instanceOnly, AbcIndexing abc, DottedChain pkg, String obj, String propertyName, Reference<String> outName, Reference<DottedChain> outNs, Reference<DottedChain> outPropNs, Reference<Integer> outPropNsKind, Reference<Integer> outPropNsIndex, Reference<GraphTargetItem> outPropType, Reference<ValueKind> outPropValue, Reference<ABC> outPropValueAbc) {
AbcIndexing.TraitIndex sp = abc.findScriptProperty(pkg.add(propertyName));
AbcIndexing.TraitIndex sp = abc.findScriptProperty(pkg.addWithSuffix(propertyName));
if (sp == null) {
sp = abc.findProperty(new AbcIndexing.PropertyDef(propertyName, new TypeItem(pkg.add(obj)), abc.getSelectedAbc(), selectedNs), !instanceOnly, true);
sp = abc.findProperty(new AbcIndexing.PropertyDef(propertyName, new TypeItem(pkg.addWithSuffix(obj)), abc.getSelectedAbc(), selectedNs), !instanceOnly, true);
}
if (sp != null) {
if (sp.objType instanceof TypeItem) {
@@ -2527,12 +2527,12 @@ public class AVM2SourceGenerator implements SourceGenerator {
}
public static void parentNames(AbcIndexing abc, int name_index, List<Integer> indices, List<String> names, List<String> namespaces, List<ABC> outABCs) {
AbcIndexing.ClassIndex ci = abc.findClass(new TypeItem(abc.getSelectedAbc().constants.getMultiname(name_index).getNameWithNamespace(abc.getSelectedAbc().constants)));
AbcIndexing.ClassIndex ci = abc.findClass(new TypeItem(abc.getSelectedAbc().constants.getMultiname(name_index).getNameWithNamespace(abc.getSelectedAbc().constants, true /*FIXME!!*/)));
while (ci != null) {
int ni = ci.abc.instance_info.get(ci.index).name_index;
indices.add(ni);
outABCs.add(ci.abc);
names.add(ci.abc.constants.getMultiname(ni).getName(ci.abc.constants, null, true));
names.add(ci.abc.constants.getMultiname(ni).getName(ci.abc.constants, null, true, true/*FIXME!!*/));
namespaces.add(ci.abc.constants.getMultiname(ni).getNamespace(ci.abc.constants).getName(ci.abc.constants).toRawString());
ci = ci.parent;
}
@@ -2627,7 +2627,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
Multiname m = ci.abc.instance_info.get(ci.index).getName(ci.abc.constants);
if (m != null) {
Namespace ns = ci.abc.instance_info.get(ci.index).getName(ci.abc.constants).getNamespace(ci.abc.constants);
String n = m.getName(ci.abc.constants, new ArrayList<>(), true);
String n = m.getName(ci.abc.constants, new ArrayList<>(), true, true /*FIXME!!*/);
String nsn = ns == null ? null : ns.getName(ci.abc.constants).toRawString();
name_index = constants.getQnameId(
n,
@@ -2638,7 +2638,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
for (int i = 1; i < constants.getMultinameCount(); i++) {
Multiname mname = constants.getMultiname(i);
if (mname != null && name.equals(mname.getName(constants, null, true))) {
if (mname != null && name.equals(mname.getName(constants, null, true, true /*FIXME!!*/))) {
if (mname.getNamespace(constants) != null && pkg.equals(mname.getNamespace(constants).getName(constants))) {
name_index = i;
break;
@@ -2648,7 +2648,7 @@ public class AVM2SourceGenerator implements SourceGenerator {
if (name_index == 0) {
if (pkg.isEmpty() && localData.currentScript != null /*FIXME!*/) {
for (Trait t : localData.currentScript.traits.traits) {
if (t.getName(abc).getName(constants, null, true).equals(name)) {
if (t.getName(abc).getName(constants, null, true, true /*FIXME!!*/).equals(name)) {
name_index = t.name_index;
break;
}
@@ -278,7 +278,7 @@ public final class AbcIndexing {
@Override
public String toString() {
return abc.constants.getMultiname(abc.instance_info.get(index).name_index).getNameWithNamespace(abc.constants).toPrintableString(true);
return abc.constants.getMultiname(abc.instance_info.get(index).name_index).getNameWithNamespace(abc.constants, true).toPrintableString(true);
}
public ClassIndex(int index, ABC abc, ClassIndex parent) {
@@ -389,7 +389,7 @@ public final class AbcIndexing {
if (ci != null && ci.parent != null && (prop.abc == null || prop.propNsIndex == 0)) {
ci = ci.parent;
//parent protected
DottedChain parentClass = ci.abc.instance_info.get(ci.index).getName(ci.abc.constants).getNameWithNamespace(ci.abc.constants);
DottedChain parentClass = ci.abc.instance_info.get(ci.index).getName(ci.abc.constants).getNameWithNamespace(ci.abc.constants, true);
TraitIndex pti = findProperty(new PropertyDef(prop.propName, new TypeItem(parentClass), ci.abc, ci.abc.instance_info.get(ci.index).protectedNS), findStatic, findInstance);
if (pti != null) {
return pti;
@@ -414,7 +414,7 @@ public final class AbcIndexing {
}
return new ApplyTypeAVM2Item(null, null, obj, params);
} else {
return new TypeItem(m.getNameWithNamespace(constants));
return new TypeItem(m.getNameWithNamespace(constants, true));
}
}
@@ -453,12 +453,12 @@ public final class AbcIndexing {
propValue = new ValueKind(tsc.value_index, tsc.value_kind);
}
if (map != null) {
PropertyDef dp = new PropertyDef(t.getName(abc).getName(abc.constants, new ArrayList<>() /*?*/, true), multinameToType(name_index, abc.constants), abc, abc.constants.getMultiname(t.name_index).namespace_index);
PropertyDef dp = new PropertyDef(t.getName(abc).getName(abc.constants, new ArrayList<>() /*?*/, true, true /*FIXME ???*/), multinameToType(name_index, abc.constants), abc, abc.constants.getMultiname(t.name_index).namespace_index);
map.put(dp, new TraitIndex(t, abc, getTraitReturnType(abc, t), propValue, multinameToType(name_index, abc.constants)));
}
if (mapNs != null) {
Multiname m = abc.constants.getMultiname(t.name_index);
PropertyNsDef ndp = new PropertyNsDef(t.getName(abc).getName(abc.constants, new ArrayList<>() /*?*/, true), m == null || m.namespace_index == 0 ? DottedChain.EMPTY : m.getNamespace(abc.constants).getName(abc.constants), abc, m == null ? 0 : m.namespace_index);
PropertyNsDef ndp = new PropertyNsDef(t.getName(abc).getName(abc.constants, new ArrayList<>() /*?*/, true, true/*FIXME ???*/), m == null || m.namespace_index == 0 ? DottedChain.EMPTY : m.getNamespace(abc.constants).getName(abc.constants), abc, m == null ? 0 : m.namespace_index);
TraitIndex ti = new TraitIndex(t, abc, getTraitReturnType(abc, t), propValue, multinameToType(name_index, abc.constants));
if (!mapNs.containsKey(ndp)) {
mapNs.put(ndp, ti);
@@ -552,7 +552,7 @@ public final class AbcIndexing {
for (ClassIndex cindex : addedClasses) {
int parentClassName = abc.instance_info.get(cindex.index).super_index;
if (parentClassName > 0) {
TypeItem parentClass = new TypeItem(abc.constants.getMultiname(parentClassName).getNameWithNamespace(abc.constants));
TypeItem parentClass = new TypeItem(abc.constants.getMultiname(parentClassName).getNameWithNamespace(abc.constants, true));
ClassIndex parentClassIndex = findClass(parentClass);
if (parentClassIndex == null) {
//Parent class can be deleted, do not check. TODO: handle this better
@@ -304,7 +304,7 @@ public class ActionScript3Parser {
s = lex();
GraphTargetItem ns = null;
if (s.type == SymbolType.NAMESPACE_OP) {
ns = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, false, null, lexer.yyline(), new DottedChain(propName), null, openedNamespaces);
ns = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, false, null, lexer.yyline(), new DottedChain(new String[]{propName}, "" /*FIXME ???*/), null, openedNamespaces);
variables.add((UnresolvedAVM2Item) ns);
s = lex();
if (s.type == SymbolType.BRACKET_OPEN) {
@@ -337,7 +337,7 @@ public class ActionScript3Parser {
private GraphTargetItem name(List<List<NamespaceItem>> allOpenedNamespaces, TypeItem thisType, NamespaceItem pkg, Reference<Boolean> needsActivation, boolean typeOnly, List<NamespaceItem> openedNamespaces, HashMap<String, Integer> registerVars, boolean inFunction, boolean inMethod, List<AssignableAVM2Item> variables, List<DottedChain> importedClasses) throws IOException, AVM2ParseException {
ParsedSymbol s = lex();
DottedChain name = new DottedChain();
DottedChain name = new DottedChain(new String[]{}, "");
String name2 = "";
if (s.type == SymbolType.ATTRIBUTE) {
name2 += "@";
@@ -348,7 +348,7 @@ public class ActionScript3Parser {
s = lex();
boolean attrBracket = false;
name = name.add(name2);
name = name.addWithSuffix(name2);
while (s.isType(SymbolType.DOT)) {
//name += s.value.toString(); //. or ::
s = lex();
@@ -371,7 +371,7 @@ public class ActionScript3Parser {
expected(s, lexer.yyline(), SymbolGroup.IDENTIFIER, SymbolType.NAMESPACE, SymbolType.MULTIPLY);
name2 += s.value.toString();
}
name = name.add(name2);
name = name.addWithSuffix(name2);
s = lex();
}
String nsname = null;
@@ -402,7 +402,7 @@ public class ActionScript3Parser {
if (attr) {
nsname = nsname.substring(1);
}
UnresolvedAVM2Item ns = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, typeOnly, null, lexer.yyline(), new DottedChain(nsname), null, openedNamespaces);
UnresolvedAVM2Item ns = new UnresolvedAVM2Item(new ArrayList<>(), importedClasses, typeOnly, null, lexer.yyline(), new DottedChain(new String[]{nsname}, ""), null, openedNamespaces);
variables.add(ns);
ret = new NamespacedAVM2Item(ns, nsprop, nspropItem, ret, attr, openedNamespaces, null);
}
@@ -618,7 +618,7 @@ public class ActionScript3Parser {
looptraits:
while (true) {
TypeItem thisType = new TypeItem(pkg.name.add(classNameStr));
TypeItem thisType = new TypeItem(pkg.name.addWithSuffix(classNameStr));
boolean isGetter = false;
boolean isSetter = false;
boolean isOverride = false;
@@ -884,13 +884,13 @@ public class ActionScript3Parser {
s = lex();
if (s.type != SymbolType.CURLY_OPEN) {
expected(s, lexer.yyline(), SymbolGroup.IDENTIFIER);
pkgName = pkgName.add(s.value.toString());
pkgName = pkgName.addWithSuffix(s.value.toString());
s = lex();
}
while (s.type == SymbolType.DOT) {
s = lex();
expected(s, lexer.yyline(), SymbolGroup.IDENTIFIER);
pkgName = pkgName.add(s.value.toString());
pkgName = pkgName.addWithSuffix(s.value.toString());
s = lex();
}
expected(s, lexer.yyline(), SymbolType.CURLY_OPEN);
@@ -1744,7 +1744,7 @@ public class ActionScript3Parser {
for (AssignableAVM2Item a : catchVars) {
if (a instanceof UnresolvedAVM2Item) {
UnresolvedAVM2Item ui = (UnresolvedAVM2Item) a;
if (ui.getVariableName().equals(DottedChain.parse(e.getVariableName()))) {
if (ui.getVariableName().equals(DottedChain.parseWithSuffix(e.getVariableName()))) {
try {
ui.resolve(null, new ArrayList<>(), new ArrayList<>(), abcIndex, new ArrayList<>(), variables);
} catch (CompilationException ex) {
@@ -1767,7 +1767,7 @@ public class ActionScript3Parser {
if (av instanceof UnresolvedAVM2Item) {
UnresolvedAVM2Item ui = (UnresolvedAVM2Item) av;
for (NameAVM2Item e : catchExceptions) {
if (ui.getVariableName().equals(DottedChain.parse(e.getVariableName()))) {
if (ui.getVariableName().equals(DottedChain.parseWithSuffix(e.getVariableName()))) {
try {
ui.resolve(null, new ArrayList<>(), new ArrayList<>(), abcIndex, new ArrayList<>(), variables);
} catch (CompilationException ex) {
@@ -2486,8 +2486,8 @@ public class ActionScript3Parser {
}
s = lex();
expected(s, lexer.yyline(), SymbolGroup.IDENTIFIER);
DottedChain fullName = new DottedChain();
fullName = fullName.add(s.value.toString());
DottedChain fullName = new DottedChain(new String[]{}, "");
fullName = fullName.addWithSuffix(s.value.toString());
s = lex();
boolean isStar = false;
while (s.type == SymbolType.DOT) {
@@ -2499,7 +2499,7 @@ public class ActionScript3Parser {
break;
}
expected(s, lexer.yyline(), SymbolGroup.IDENTIFIER);
fullName = fullName.add(s.value.toString());
fullName = fullName.addWithSuffix(s.value.toString());
s = lex();
}
@@ -134,7 +134,7 @@ public class CallAVM2Item extends AVM2Item {
}
}
if (cname != null && AVM2SourceGenerator.searchPrototypeChain(otherNs, localData.privateNs, localData.protectedNs, true, g.abcIndex, pkgName, cname, prop.propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc) && (localData.getFullClass().equals(outNs.getVal().add(outName.getVal()).toRawString()))) {
if (cname != null && AVM2SourceGenerator.searchPrototypeChain(otherNs, localData.privateNs, localData.protectedNs, true, g.abcIndex, pkgName, cname, prop.propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc) && (localData.getFullClass().equals(outNs.getVal().addWithSuffix(outName.getVal()).toRawString()))) {
NameAVM2Item nobj = new NameAVM2Item(new TypeItem(localData.getFullClass()), 0, "this", null, false, new ArrayList<>());
nobj.setRegNumber(0);
obj = nobj;
@@ -65,7 +65,7 @@ public class ConstructSomethingAVM2Item extends CallAVM2Item {
if (resname instanceof TypeItem) {
TypeItem prop = (TypeItem) resname;
if (localData.isStatic && localData.pkg.add(localData.currentClass).equals(prop.fullTypeName)) {
if (localData.isStatic && localData.pkg.addWithSuffix(localData.currentClass).equals(prop.fullTypeName)) {
return toSourceMerge(localData, generator,
new AVM2Instruction(0, AVM2Instructions.GetLocal0, new int[]{}), arguments,
new AVM2Instruction(0, AVM2Instructions.Construct, new int[]{arguments.size()}));
@@ -49,7 +49,7 @@ public class NamespaceItem {
}
public NamespaceItem(String name, int kind) {
this.name = DottedChain.parse(name);
this.name = DottedChain.parseWithSuffix(name);
this.kind = kind;
}
@@ -119,7 +119,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
}
return new ApplyTypeAVM2Item(null, null, obj, params);
} else {
return new TypeItem(m.getNameWithNamespace(constants));
return new TypeItem(m.getNameWithNamespace(constants, true));
}
}
@@ -245,7 +245,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
}
}
if (AVM2SourceGenerator.searchPrototypeChain(otherNs, localData.privateNs, localData.protectedNs, false, abcIndex, ftn.getWithoutLast(), ftn.getLast(), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc)) {
objType = new TypeItem(outNs.getVal().add(outName.getVal()));
objType = new TypeItem(outNs.getVal().addWithSuffix(outName.getVal()));
propType = outPropType.getVal();
propIndex = constants.getMultinameId(Multiname.createQName(false,
constants.getStringId(propertyName, true),
@@ -260,7 +260,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
for (MethodBody b : callStack) {
for (int i = 0; i < b.traits.traits.size(); i++) {
Trait t = b.traits.traits.get(i);
if (t.getName(abc).getName(constants, null, true).equals(propertyName)) {
if (t.getName(abc).getName(constants, null, true, true).equals(propertyName)) {
if (t instanceof TraitSlotConst) {
TraitSlotConst tsc = (TraitSlotConst) t;
objType = new TypeItem(DottedChain.FUNCTION);
@@ -287,7 +287,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
int name_index = 0;
for (int m = 1; m < constants.getMultinameCount(); m++) {
Multiname mname = constants.getMultiname(m);
if (mname.kind == Multiname.QNAME && mname.getName(constants, null, true).equals(propertyName) && mname.namespace_index == nsindex) {
if (mname.kind == Multiname.QNAME && mname.getName(constants, null, true, true).equals(propertyName) && mname.namespace_index == nsindex) {
name_index = m;
break;
}
@@ -363,7 +363,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
}
}
if (AVM2SourceGenerator.searchPrototypeChain(otherns, localData.privateNs, localData.protectedNs, false, abcIndex, nsname, (((TypeItem) p.objType).fullTypeName.getLast()), propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc)) {
objType = new TypeItem(outNs.getVal().add(outName.getVal()));
objType = new TypeItem(outNs.getVal().addWithSuffix(outName.getVal()));
propType = p.returnType;
propIndex = constants.getMultinameId(Multiname.createQName(false,
constants.getStringId(propertyName, true),
@@ -683,7 +683,7 @@ public class PropertyAVM2Item extends AssignableAVM2Item {
otherNs.add(n.getCpoolIndex(abcIndex));
}
}
if (!localData.subMethod && cname != null && AVM2SourceGenerator.searchPrototypeChain(otherNs, localData.privateNs, localData.protectedNs, true, abcIndex, pkgName, cname, propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc) && (localData.getFullClass().equals(outNs.getVal().add(outName.getVal()).toRawString()))) {
if (!localData.subMethod && cname != null && AVM2SourceGenerator.searchPrototypeChain(otherNs, localData.privateNs, localData.protectedNs, true, abcIndex, pkgName, cname, propertyName, outName, outNs, outPropNs, outPropNsKind, outPropNsIndex, outPropType, outPropValue, outPropValueAbc) && (localData.getFullClass().equals(outNs.getVal().addWithSuffix(outName.getVal()).toRawString()))) {
NameAVM2Item nobj = new NameAVM2Item(new TypeItem(localData.getFullClass()), 0, "this", null, false, openedNamespaces);
nobj.setRegNumber(0);
obj = nobj;
@@ -35,5 +35,6 @@ public enum SymbolGroup {
//GLOBALFUNC,
GLOBALCONST,
PREPROCESSOR,
REGEXP
REGEXP,
NAMESPACESUFFIX
}
@@ -207,7 +207,8 @@ public enum SymbolType {
DESCENDANTS(GraphTargetItem.PRECEDENCE_PRIMARY, false),
NATIVE,
PREPROCESSOR(GraphTargetItem.PRECEDENCE_PRIMARY, false),
REGEXP(GraphTargetItem.PRECEDENCE_PRIMARY, false);
REGEXP(GraphTargetItem.PRECEDENCE_PRIMARY, false),
NAMESPACESUFFIX;
private int precedence = GraphTargetItem.NOPRECEDENCE;
@@ -123,7 +123,7 @@ public class UnresolvedAVM2Item extends AssignableAVM2Item {
}
*/
public void appendName(String name) {
this.name = this.name.add(name);
this.name = this.name.addWithSuffix(name);
}
public void setDefinition(boolean definition) {
@@ -354,7 +354,7 @@ public class UnresolvedAVM2Item extends AssignableAVM2Item {
//Search for types in opened namespaces
for (NamespaceItem n : openedNamespaces) {
Namespace ons = abc.getSelectedAbc().constants.getNamespace(n.getCpoolIndex(abc));
TypeItem ti = new TypeItem(ons.getName(abc.getSelectedAbc().constants).add(name.get(0)));
TypeItem ti = new TypeItem(ons.getName(abc.getSelectedAbc().constants).addWithSuffix(name.get(0)));
AbcIndexing.ClassIndex ci = abc.findClass(ti);
if (ci != null) {
if (!subtypes.isEmpty() && name.size() > 1) {
@@ -393,7 +393,7 @@ public class UnresolvedAVM2Item extends AssignableAVM2Item {
if (ci == null) {
ntype = new TypeItem("Object");
} else {
ntype = new TypeItem(ci.abc.instance_info.get(ci.index).getName(ci.abc.constants).getNameWithNamespace(ci.abc.constants));
ntype = new TypeItem(ci.abc.instance_info.get(ci.index).getName(ci.abc.constants).getNameWithNamespace(ci.abc.constants, true));
}
}
@@ -65,14 +65,14 @@ public class ABCException implements Serializable, Cloneable {
if (name_index == 0) {
return "";
}
return constants.getMultiname(name_index).getName(constants, fullyQualifiedNames, false);
return constants.getMultiname(name_index).getName(constants, fullyQualifiedNames, false, true);
}
public String getTypeName(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames) {
if (type_index == 0) {
return "*";
}
return constants.getMultiname(type_index).getName(constants, fullyQualifiedNames, false);
return constants.getMultiname(type_index).getName(constants, fullyQualifiedNames, false, true);
}
@Override
@@ -103,11 +103,11 @@ public class InstanceInfo {
}
writer.appendNoHilight(modifiers + objType);
writer.hilightSpecial(abc.constants.getMultiname(name_index).getName(abc.constants, null/* No full names here*/, false), HighlightSpecialType.CLASS_NAME);
writer.hilightSpecial(abc.constants.getMultiname(name_index).getName(abc.constants, null/* No full names here*/, false, true), HighlightSpecialType.CLASS_NAME);
if (super_index > 0) {
String typeName = abc.constants.getMultiname(super_index).getNameWithNamespace(abc.constants).toRawString();
String parentName = abc.constants.getMultiname(super_index).getName(abc.constants, fullyQualifiedNames, false);
String typeName = abc.constants.getMultiname(super_index).getNameWithNamespace(abc.constants, true).toRawString();
String parentName = abc.constants.getMultiname(super_index).getName(abc.constants, fullyQualifiedNames, false, true);
if (!parentName.equals("Object")) {
writer.appendNoHilight(" extends ");
writer.hilightSpecial(parentName, HighlightSpecialType.TYPE_NAME, typeName);
@@ -123,8 +123,8 @@ public class InstanceInfo {
if (i > 0) {
writer.append(", ");
}
String typeName = abc.constants.getMultiname(interfaces[i]).getNameWithNamespace(abc.constants).toRawString();
writer.hilightSpecial(abc.constants.getMultiname(interfaces[i]).getName(abc.constants, fullyQualifiedNames, false), HighlightSpecialType.TYPE_NAME, typeName);
String typeName = abc.constants.getMultiname(interfaces[i]).getNameWithNamespace(abc.constants, true).toRawString();
writer.hilightSpecial(abc.constants.getMultiname(interfaces[i]).getName(abc.constants, fullyQualifiedNames, false, true), HighlightSpecialType.TYPE_NAME, typeName);
}
}
@@ -319,7 +319,7 @@ public class MethodInfo {
}
DottedChain ptype = DottedChain.ALL;
if (param_types[i] > 0) {
ptype = constants.getMultiname(param_types[i]).getNameWithNamespace(constants);
ptype = constants.getMultiname(param_types[i]).getNameWithNamespace(constants, true);
}
HighlightData pdata = new HighlightData();
@@ -340,7 +340,7 @@ public class MethodInfo {
if (param_types[i] == 0) {
writer.hilightSpecial("*", HighlightSpecialType.PARAM, i);
} else {
writer.hilightSpecial(constants.getMultiname(param_types[i]).getName(constants, fullyQualifiedNames, false), HighlightSpecialType.PARAM, i);
writer.hilightSpecial(constants.getMultiname(param_types[i]).getName(constants, fullyQualifiedNames, false, true), HighlightSpecialType.PARAM, i);
}
if (optional != null) {
if (i >= param_types.length - optional.length) {
@@ -381,7 +381,7 @@ public class MethodInfo {
if (multiname.kind != Multiname.TYPENAME && multiname.name_index > 0 && constants.getString(multiname.name_index).equals("void")) {
rname = "void";
} else {
rname = multiname.getName(constants, fullyQualifiedNames, false);
rname = multiname.getName(constants, fullyQualifiedNames, false, true);
}
}
return writer.hilightSpecial(rname, HighlightSpecialType.RETURNS);
@@ -394,7 +394,7 @@ public class MethodInfo {
if (multiname.kind != Multiname.TYPENAME && multiname.name_index > 0 && constants.getString(multiname.name_index).equals("void")) {
rname = "void";
} else {
rname = multiname.getName(constants, fullyQualifiedNames, false);
rname = multiname.getName(constants, fullyQualifiedNames, false, true);
}
}
return rname;
@@ -73,6 +73,20 @@ public class Multiname {
@Internal
public boolean deleted;
@Internal
private boolean displayNamespace = false;
public String getNamespaceSuffix() {
if (displayNamespace) {
return "#" + namespace_index;
}
return "";
}
public void setDisplayNamespace(boolean displayNamespace) {
this.displayNamespace = displayNamespace;
}
private boolean validType() {
boolean cnt = false;
for (int i = 0; i < multinameKinds.length; i++) {
@@ -103,6 +117,18 @@ public class Multiname {
}
}
public boolean hasOwnName() {
return kind == QNAME || kind == QNAMEA || kind == RTQNAME || kind == RTQNAMEA || kind == MULTINAME || kind == MULTINAMEA;
}
public boolean hasOwnNamespace() {
return kind == QNAME || kind == QNAMEA;
}
public boolean hasOwnNamespaceSet() {
return kind == MULTINAME || kind == MULTINAMEA || kind == MULTINAMEL || kind == MULTINAMELA;
}
public static Multiname createQName(boolean attribute, int name_index, int namespace_index) {
return new Multiname(attribute ? QNAMEA : QNAME, name_index, namespace_index, 0, 0, null);
}
@@ -300,12 +326,12 @@ public class Multiname {
return null;
}
private String typeNameToStr(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames, boolean raw) {
private String typeNameToStr(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames, boolean dontDeobfuscate, boolean withSuffix) {
if (constants.getMultiname(qname_index).name_index == name_index) {
return "ambiguousTypeName";
}
StringBuilder typeNameStr = new StringBuilder();
typeNameStr.append(constants.getMultiname(qname_index).getName(constants, fullyQualifiedNames, raw));
typeNameStr.append(constants.getMultiname(qname_index).getName(constants, fullyQualifiedNames, dontDeobfuscate, withSuffix));
if (params != null && params.length > 0) {
typeNameStr.append(".<");
for (int i = 0; i < params.length; i++) {
@@ -316,7 +342,7 @@ public class Multiname {
if (param == 0) {
typeNameStr.append("*");
} else {
typeNameStr.append(constants.getMultiname(param).getName(constants, fullyQualifiedNames, raw));
typeNameStr.append(constants.getMultiname(param).getName(constants, fullyQualifiedNames, dontDeobfuscate, withSuffix));
}
}
typeNameStr.append(">");
@@ -324,9 +350,9 @@ public class Multiname {
return typeNameStr.toString();
}
public String getName(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames, boolean raw) {
public String getName(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames, boolean dontDeobfuscate, boolean withSuffix) {
if (kind == TYPENAME) {
return typeNameToStr(constants, fullyQualifiedNames, raw);
return typeNameToStr(constants, fullyQualifiedNames, dontDeobfuscate, withSuffix);
}
if (name_index == -1) {
return "";
@@ -335,15 +361,15 @@ public class Multiname {
return isAttribute() ? "@*" : "*";
} else {
String name = constants.getString(name_index);
if (fullyQualifiedNames != null && fullyQualifiedNames.contains(DottedChain.parse(name))) {
DottedChain dc = getNameWithNamespace(constants);
return raw ? dc.toRawString() : dc.toPrintableString(true);
if (fullyQualifiedNames != null && fullyQualifiedNames.contains(DottedChain.parseWithSuffix(name))) {
DottedChain dc = getNameWithNamespace(constants, withSuffix);
return dontDeobfuscate ? dc.toRawString() : dc.toPrintableString(true);
}
return (isAttribute() ? "@" : "") + (raw ? name : IdentifiersDeobfuscation.printIdentifier(true, name));
return (isAttribute() ? "@" : "") + (dontDeobfuscate ? name : IdentifiersDeobfuscation.printIdentifier(true, name)) + (withSuffix ? getNamespaceSuffix() : "");
}
}
public DottedChain getNameWithNamespace(AVM2ConstantPool constants) {
public DottedChain getNameWithNamespace(AVM2ConstantPool constants, boolean withSuffix) {
Namespace ns = getNamespace(constants);
if (ns == null) {
NamespaceSet nss = getNamespaceSet(constants);
@@ -353,11 +379,11 @@ public class Multiname {
}
}
}
String name = getName(constants, null, true);
String name = getName(constants, null, false, false);
if (ns != null) {
return ns.getName(constants).add(name);
return ns.getName(constants).add(name, withSuffix ? getNamespaceSuffix() : "");
}
return new DottedChain(name);
return new DottedChain(new String[]{name}, withSuffix ? getNamespaceSuffix() : "");
}
public Namespace getNamespace(AVM2ConstantPool constants) {
@@ -481,7 +507,7 @@ public class Multiname {
return false;
}
if (!Objects.equals(other.getName(otherCpool, new ArrayList<>(), true), getName(thisCpool, new ArrayList<>(), true))) {
if (!Objects.equals(other.getName(otherCpool, new ArrayList<>(), true, true), getName(thisCpool, new ArrayList<>(), true, true))) {
return false;
}
@@ -78,7 +78,8 @@ public class ScriptInfo {
if ((ns.kind == Namespace.KIND_PACKAGE_INTERNAL)
|| (ns.kind == Namespace.KIND_PACKAGE)) {
DottedChain packageName = ns.getName(abc.constants); // assume not null package
String objectName = name.getName(abc.constants, null, true);
String objectName = name.getName(abc.constants, null, true, false);
String namespaceSuffix = name.getNamespaceSuffix();
List<Integer> traitIndices = new ArrayList<>();
traitIndices.add(j);
@@ -88,7 +89,7 @@ public class ScriptInfo {
}
if (packagePrefix == null || packageName.toPrintableString(true).startsWith(packagePrefix)) {
ClassPath cp = new ClassPath(packageName, objectName);
ClassPath cp = new ClassPath(packageName, objectName, namespaceSuffix);
ret.add(new ScriptPack(cp, abc, allAbcs, scriptIndex, traitIndices));
}
}
@@ -96,6 +97,24 @@ public class ScriptInfo {
if (ret.size() == 1) {
ret.get(0).isSimple = true;
}
if (ret.isEmpty() && !otherTraits.isEmpty()) { //no public/package internal traits to determine common pack name
//make each trait separate pack
for (int traitIndex : otherTraits) {
Trait t = traits.traits.get(traitIndex);
Multiname name = t.getName(abc);
Namespace ns = name.getNamespace(abc.constants);
DottedChain packageName = ns.getName(abc.constants);
String objectName = name.getName(abc.constants, null, true, false);
String namespaceSuffix = name.getNamespaceSuffix();
List<Integer> traitIndices = new ArrayList<>();
traitIndices.add(traitIndex);
ClassPath cp = new ClassPath(packageName, objectName, namespaceSuffix);
ret.add(new ScriptPack(cp, abc, allAbcs, scriptIndex, traitIndices));
}
}
return ret;
}
@@ -118,11 +118,11 @@ public abstract class Trait implements Cloneable, Serializable {
public var attr2;
*/
if (parent instanceof TraitClass) {
String thisName = getName(abc).getName(abc.constants, new ArrayList<>(), true);
String thisName = getName(abc).getName(abc.constants, new ArrayList<>(), true, true);
List<Trait> classTraits = abc.class_info.get(((TraitClass) parent).class_info).static_traits.traits;
for (Trait t : classTraits) {
if (t.kindType == Trait.TRAIT_SLOT) {
if ("_skinParts".equals(t.getName(abc).getName(abc.constants, new ArrayList<>(), true))) {
if ("_skinParts".equals(t.getName(abc).getName(abc.constants, new ArrayList<>(), true, true))) {
if (t.getName(abc).getNamespace(abc.constants).kind == Namespace.KIND_PRIVATE) {
if (convertData.assignedValues.containsKey(t)) {
if (convertData.assignedValues.get(t).value instanceof NewObjectAVM2Item) {
@@ -233,7 +233,7 @@ public abstract class Trait implements Cloneable, Serializable {
if (importnames.contains(name)) {
imports.remove(i);
i--;
fullyQualifiedNames.add(new DottedChain(name));
fullyQualifiedNames.add(DottedChain.parseWithSuffix(name));
} else {
importnames.add(name);
}
@@ -246,7 +246,7 @@ public abstract class Trait implements Cloneable, Serializable {
if (name.equals("*")) {
continue;
}
DottedChain dAll = pkg.add("*");
DottedChain dAll = pkg.addWithSuffix("*");
if (imports.contains(dAll)) {
imports.remove(i);
i--;
@@ -491,8 +491,9 @@ public abstract class Trait implements Cloneable, Serializable {
Multiname name = getName(abc);
Namespace ns = name.getNamespace(abc.constants);
DottedChain packageName = ns == null ? DottedChain.EMPTY : ns.getName(abc.constants);
String objectName = name.getName(abc.constants, null, true);
return new ClassPath(packageName, objectName); //assume not null name
String objectName = name.getName(abc.constants, null, true, false);
String namespaceSuffix = name.getNamespaceSuffix();
return new ClassPath(packageName, objectName, namespaceSuffix); //assume not null name
}
@Override
@@ -114,7 +114,7 @@ public class TraitClass extends Trait implements TraitWithSlot {
fullyQualifiedNames = new ArrayList<>();
writeImportsUsages(abc, writer, packageName, fullyQualifiedNames);
String instanceInfoName = instanceInfoMultiname.getName(abc.constants, fullyQualifiedNames, false);
String instanceInfoName = instanceInfoMultiname.getName(abc.constants, fullyQualifiedNames, false, true);
writer.startClass(class_info);
@@ -175,7 +175,7 @@ public class TraitClass extends Trait implements TraitWithSlot {
writer.startMethod(instanceInfo.iinit_index);
writer.appendNoHilight(modifier);
writer.appendNoHilight("function ");
writer.appendNoHilight(m.getName(abc.constants, null/*do not want full names here*/, false));
writer.appendNoHilight(m.getName(abc.constants, null/*do not want full names here*/, false, true));
writer.appendNoHilight("(");
bodyIndex = abc.findBodyIndex(instanceInfo.iinit_index);
MethodBody body = bodyIndex == -1 ? null : abc.bodies.get(bodyIndex);
@@ -210,12 +210,12 @@ public class TraitClass extends Trait implements TraitWithSlot {
fullyQualifiedNames = new ArrayList<>();
InstanceInfo instanceInfo = abc.instance_info.get(class_info);
String instanceInfoName = instanceInfo.getName(abc.constants).getName(abc.constants, fullyQualifiedNames, false);
String instanceInfoName = instanceInfo.getName(abc.constants).getName(abc.constants, fullyQualifiedNames, false, true);
ClassInfo classInfo = abc.class_info.get(class_info);
AbcIndexing index = new AbcIndexing(abc.getSwf());
//for simplification of String(this)
convertData.thisHasDefaultToPrimitive = null == index.findProperty(new AbcIndexing.PropertyDef("toString", new TypeItem(instanceInfo.getName(abc.constants).getNameWithNamespace(abc.constants)), abc, abc.constants.getNamespaceId(Namespace.KIND_PACKAGE, DottedChain.TOPLEVEL, abc.constants.getStringId("", true), true)), false, true);
convertData.thisHasDefaultToPrimitive = null == index.findProperty(new AbcIndexing.PropertyDef("toString", new TypeItem(instanceInfo.getName(abc.constants).getNameWithNamespace(abc.constants, true)), abc, abc.constants.getNamespaceId(Namespace.KIND_PACKAGE, DottedChain.TOPLEVEL, abc.constants.getStringId("", true), true)), false, true);
//class initializer
int bodyIndex = abc.findBodyIndex(classInfo.cinit_index);
@@ -65,7 +65,7 @@ public class TraitFunction extends Trait implements TraitWithSlot {
}
getModifiers(abc, isStatic, writer);
writer.hilightSpecial("function ", HighlightSpecialType.TRAIT_TYPE);
writer.hilightSpecial(abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false), HighlightSpecialType.TRAIT_NAME);
writer.hilightSpecial(abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false, true), HighlightSpecialType.TRAIT_NAME);
writer.appendNoHilight("(");
abc.method_info.get(method_info).getParamStr(writer, abc.constants, body, abc, fullyQualifiedNames);
writer.appendNoHilight(") : ");
@@ -87,7 +87,7 @@ public class TraitFunction extends Trait implements TraitWithSlot {
writer.startBlock();
int bodyIndex = abc.findBodyIndex(method_info);
if (bodyIndex != -1) {
abc.bodies.get(bodyIndex).toString(path + "." + abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false), exportMode, abc, this, writer, fullyQualifiedNames);
abc.bodies.get(bodyIndex).toString(path + "." + abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false, true), exportMode, abc, this, writer, fullyQualifiedNames);
}
writer.endBlock();
@@ -104,7 +104,7 @@ public class TraitFunction extends Trait implements TraitWithSlot {
convertHeader(parent, convertData, path, abc, isStatic, exportMode, scriptIndex, classIndex, writer, fullyQualifiedNames, parallel);
int bodyIndex = abc.findBodyIndex(method_info);
if (bodyIndex != -1) {
abc.bodies.get(bodyIndex).convert(convertData, path + "." + abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false), exportMode, isStatic, method_info, scriptIndex, classIndex, abc, this, new ScopeStack(), 0, writer, fullyQualifiedNames, null, true);
abc.bodies.get(bodyIndex).convert(convertData, path + "." + abc.constants.getMultiname(name_index).getName(abc.constants, fullyQualifiedNames, false, true), exportMode, isStatic, method_info, scriptIndex, classIndex, abc, this, new ScopeStack(), 0, writer, fullyQualifiedNames, null, true);
}
writer.endMethod();
}
@@ -95,7 +95,7 @@ public class TraitMethodGetterSetter extends Trait {
getModifiers(abc, isStatic, writer);
writer.hilightSpecial("function " + addKind, HighlightSpecialType.TRAIT_TYPE);
writer.hilightSpecial(getName(abc).getName(abc.constants, fullyQualifiedNames, false), HighlightSpecialType.TRAIT_NAME);
writer.hilightSpecial(getName(abc).getName(abc.constants, fullyQualifiedNames, false, true), HighlightSpecialType.TRAIT_NAME);
writer.appendNoHilight("(");
abc.method_info.get(method_info).getParamStr(writer, abc.constants, body, abc, fullyQualifiedNames);
writer.appendNoHilight(") : ");
@@ -109,7 +109,7 @@ public class TraitMethodGetterSetter extends Trait {
writeImportsUsages(abc, writer, getPackage(abc), fullyQualifiedNames);
}
writer.startMethod(method_info);
path = path + "." + getName(abc).getName(abc.constants, fullyQualifiedNames, false);
path = path + "." + getName(abc).getName(abc.constants, fullyQualifiedNames, false, true);
convertHeader(parent, convertData, path, abc, isStatic, exportMode, scriptIndex, classIndex, writer, fullyQualifiedNames, parallel);
int bodyIndex = abc.findBodyIndex(method_info);
if (exportMode != ScriptExportMode.AS_METHOD_STUBS) {
@@ -130,7 +130,7 @@ public class TraitMethodGetterSetter extends Trait {
}
getMetaData(parent, convertData, abc, writer);
writer.startMethod(method_info);
path = path + "." + getName(abc).getName(abc.constants, fullyQualifiedNames, false);
path = path + "." + getName(abc).getName(abc.constants, fullyQualifiedNames, false, true);
toStringHeader(parent, convertData, path, abc, isStatic, exportMode, scriptIndex, classIndex, writer, fullyQualifiedNames, parallel);
int bodyIndex = abc.findBodyIndex(method_info);
if (classIndex != -1 && abc.instance_info.get(classIndex).isInterface() || bodyIndex == -1) {
@@ -190,10 +190,10 @@ public class TraitMethodGetterSetter extends Trait {
@Override
public boolean isVisible(boolean isStatic, ABC abc) {
if (Configuration.handleSkinPartsAutomatically.get()) {
if ("skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true))) {
if ("skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true, true))) {
if (kindType == TRAIT_GETTER) {
MethodInfo mi = abc.method_info.get(method_info);
if (mi.param_types.length == 0 && "Object".equals(abc.constants.getMultiname(mi.ret_type).getNameWithNamespace(abc.constants).toRawString())) {
if (mi.param_types.length == 0 && "Object".equals(abc.constants.getMultiname(mi.ret_type).getNameWithNamespace(abc.constants, true).toRawString())) {
if (abc.constants.getNamespace(abc.constants.getMultiname(name_index).namespace_index).kind == Namespace.KIND_PROTECTED) {
return false;
}
@@ -76,7 +76,7 @@ public class TraitSlotConst extends Trait implements TraitWithSlot {
public String getType(AVM2ConstantPool constants, List<DottedChain> fullyQualifiedNames) {
String typeStr = "*";
if (type_index > 0) {
typeStr = constants.getMultiname(type_index).getName(constants, fullyQualifiedNames, false);
typeStr = constants.getMultiname(type_index).getName(constants, fullyQualifiedNames, false, true);
}
return typeStr;
}
@@ -101,7 +101,7 @@ public class TraitSlotConst extends Trait implements TraitWithSlot {
slotconst = "namespace";
}
writer.hilightSpecial(slotconst + " ", HighlightSpecialType.TRAIT_TYPE);
writer.hilightSpecial(getName(abc).getName(abc.constants, fullyQualifiedNames, false), HighlightSpecialType.TRAIT_NAME);
writer.hilightSpecial(getName(abc).getName(abc.constants, fullyQualifiedNames, false, true), HighlightSpecialType.TRAIT_NAME);
writer.hilightSpecial(typeStr, HighlightSpecialType.TRAIT_TYPE_NAME);
return writer;
}
@@ -216,9 +216,9 @@ public class TraitSlotConst extends Trait implements TraitWithSlot {
Hide: private static var _skinParts
(part of [SkinPart] compilations)
*/
if (isStatic && "_skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true))) {
if (isStatic && "_skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true, true))) {
if (kindType == Trait.TRAIT_SLOT) {
if ("_skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true))) {
if ("_skinParts".equals(getName(abc).getName(abc.constants, new ArrayList<>(), true, true))) {
if (getName(abc).getNamespace(abc.constants).kind == Namespace.KIND_PRIVATE) {
return false;
}
@@ -22,28 +22,36 @@ import com.jpexs.decompiler.flash.abc.ABC;
*
* @author JPEXS
*/
public abstract class InsideClassMultinameUsage extends MultinameUsage {
public class ClassNameInTraitMultinameUsage extends MultinameUsage implements DefinitionUsage, InsideClassMultinameUsageInterface {
public int multinameIndex;
private int classIndex;
public int classIndex;
public InsideClassMultinameUsage(ABC abc, int multinameIndex, int classIndex) {
super(abc);
this.multinameIndex = multinameIndex;
public ClassNameInTraitMultinameUsage(ABC abc, int multinameIndex, int classIndex) {
super(abc, multinameIndex);
this.classIndex = classIndex;
}
@Override
public String toString() {
return "class " + abc.constants.getMultiname(abc.instance_info.get(classIndex).name_index).getNameWithNamespace(abc.constants).toPrintableString(true);
}
public int getMultinameIndex() {
return multinameIndex;
}
public int getClassIndex() {
return classIndex;
}
@Override
public String toString() {
return "class " + abc.constants.getMultiname(abc.instance_info.get(classIndex).name_index).getNameWithNamespace(abc.constants, true).toPrintableString(true) + " trait name";
}
@Override
public boolean collides(MultinameUsage other) {
if (other instanceof InsideClassMultinameUsageInterface) {
if (((InsideClassMultinameUsageInterface) other).getClassIndex() == getClassIndex()) {
return false;
}
}
if ((other instanceof ClassNameInTraitMultinameUsage) || (other instanceof ClassNameMultinameUsage)) {
return sameMultinameName(other);
}
return false;
}
}
@@ -22,14 +22,36 @@ import com.jpexs.decompiler.flash.abc.ABC;
*
* @author JPEXS
*/
public class ClassNameMultinameUsage extends InsideClassMultinameUsage implements DefinitionUsage {
public class ClassNameMultinameUsage extends MultinameUsage implements DefinitionUsage, InsideClassMultinameUsageInterface {
private int classIndex;
public ClassNameMultinameUsage(ABC abc, int multinameIndex, int classIndex) {
super(abc, multinameIndex, classIndex);
super(abc, multinameIndex);
this.classIndex = classIndex;
}
@Override
public int getClassIndex() {
return classIndex;
}
@Override
public String toString() {
return "class " + abc.constants.getMultiname(abc.instance_info.get(classIndex).name_index).getNameWithNamespace(abc.constants).toPrintableString(true);
return "class " + abc.constants.getMultiname(abc.instance_info.get(classIndex).name_index).getNameWithNamespace(abc.constants, true).toPrintableString(true);
}
@Override
public boolean collides(MultinameUsage other) {
if (other instanceof InsideClassMultinameUsageInterface) {
if (((InsideClassMultinameUsageInterface) other).getClassIndex() == getClassIndex()) {
return false;
}
}
if ((other instanceof ClassNameInTraitMultinameUsage) || (other instanceof ClassNameMultinameUsage)) {
return sameMultinameName(other);
}
return false;
}
}
@@ -33,8 +33,8 @@ import java.util.ArrayList;
*/
public abstract class ConstVarMultinameUsage extends TraitMultinameUsage {
public ConstVarMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, traits, parentTraitIndex);
public ConstVarMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, traits, parentTraitIndex);
}
@Override
@@ -42,14 +42,14 @@ public abstract class ConstVarMultinameUsage extends TraitMultinameUsage {
NulWriter nulWriter = new NulWriter();
ConvertData convertData = new ConvertData();
if (parentTraitIndex > -1) {
if (isStatic) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
} else {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
if (traitsType == TRAITS_TYPE_CLASS) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
} else if (traitsType == TRAITS_TYPE_INSTANCE) {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
}
}
try {
((TraitSlotConst) traits.traits.get(traitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
((TraitSlotConst) traits.traits.get(traitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS /*?? FIXME*/, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
} catch (InterruptedException ex) {
// ignore
}
@@ -57,18 +57,18 @@ public abstract class ConstVarMultinameUsage extends TraitMultinameUsage {
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), false);
writer.appendNoHilight(super.toString() + " ");
if (parentTraitIndex > -1) {
if (isStatic) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
} else {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
if (traitsType == TRAITS_TYPE_CLASS) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
} else if (traitsType == TRAITS_TYPE_INSTANCE) {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
}
}
try {
((TraitSlotConst) traits.traits.get(traitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
((TraitSlotConst) traits.traits.get(traitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
} catch (InterruptedException ex) {
// ignore
}
return writer.toString();
return writer.toString().trim();
}
public int getTraitIndex() {
@@ -76,6 +76,6 @@ public abstract class ConstVarMultinameUsage extends TraitMultinameUsage {
}
public boolean isStatic() {
return isStatic;
return traitsType == TRAITS_TYPE_CLASS;
}
}
@@ -25,12 +25,26 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class ConstVarNameMultinameUsage extends ConstVarMultinameUsage implements DefinitionUsage {
public ConstVarNameMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, traits, parentTraitIndex);
public ConstVarNameMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, traits, parentTraitIndex);
}
@Override
public String toString() {
return super.toString() + " name";
}
@Override
public boolean collides(MultinameUsage other) {
if ((other instanceof ConstVarNameMultinameUsage) || (other instanceof MethodNameMultinameUsage)) {
TraitMultinameUsage otherTrait = (TraitMultinameUsage) other;
if (otherTrait.classIndex == classIndex && otherTrait.traitsType == traitsType && otherTrait.parentTraitIndex == parentTraitIndex) {
if (other.sameMultinameName(this)) {
return true;
}
}
}
return false;
}
}
@@ -25,12 +25,18 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class ConstVarTypeMultinameUsage extends ConstVarMultinameUsage {
public ConstVarTypeMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, traits, parentTraitIndex);
public ConstVarTypeMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, traits, parentTraitIndex);
}
@Override
public String toString() {
return super.toString() + " type";
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
}
@@ -22,14 +22,28 @@ import com.jpexs.decompiler.flash.abc.ABC;
*
* @author JPEXS
*/
public class ExtendsMultinameUsage extends InsideClassMultinameUsage {
public class ExtendsMultinameUsage extends MultinameUsage implements InsideClassMultinameUsageInterface {
private int classIndex;
public ExtendsMultinameUsage(ABC abc, int multinameIndex, int classIndex) {
super(abc, multinameIndex, classIndex);
super(abc, multinameIndex);
this.classIndex = classIndex;
}
@Override
public int getClassIndex() {
return classIndex;
}
@Override
public String toString() {
return super.toString() + " extends";
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
}
@@ -22,14 +22,28 @@ import com.jpexs.decompiler.flash.abc.ABC;
*
* @author JPEXS
*/
public class ImplementsMultinameUsage extends InsideClassMultinameUsage {
public class ImplementsMultinameUsage extends MultinameUsage implements InsideClassMultinameUsageInterface {
private int classIndex;
public ImplementsMultinameUsage(ABC abc, int multinameIndex, int classIndex) {
super(abc, multinameIndex, classIndex);
super(abc, multinameIndex);
this.classIndex = classIndex;
}
@Override
public int getClassIndex() {
return classIndex;
}
@Override
public String toString() {
return super.toString() + " implements";
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
}
@@ -0,0 +1,30 @@
/*
* Copyright (C) 2010-2016 JPEXS, All rights reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3.0 of the License, or (at your option) any later version.
*
* This library 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library.
*/
package com.jpexs.decompiler.flash.abc.usages;
import com.jpexs.decompiler.flash.abc.ABC;
/**
*
* @author JPEXS
*/
public interface InsideClassMultinameUsageInterface {
public int getClassIndex();
public ABC getAbc();
}
@@ -25,12 +25,18 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class MethodBodyMultinameUsage extends MethodMultinameUsage {
public MethodBodyMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex);
public MethodBodyMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex);
}
@Override
public String toString() {
return super.toString() + " body";
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
}
@@ -34,8 +34,8 @@ public abstract class MethodMultinameUsage extends TraitMultinameUsage {
public boolean isInitializer;
public MethodMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, traits, parentTraitIndex);
public MethodMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, traits, parentTraitIndex);
this.isInitializer = isInitializer;
}
@@ -49,36 +49,44 @@ public abstract class MethodMultinameUsage extends TraitMultinameUsage {
ConvertData convertData = new ConvertData();
if (!isInitializer) {
if (parentTraitIndex > -1) {
if (isStatic) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
if (traitsType == TRAITS_TYPE_CLASS) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
} else {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
}
}
((TraitMethodGetterSetter) traits.traits.get(traitIndex)).convertHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
((TraitMethodGetterSetter) traits.traits.get(traitIndex)).convertHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, nulWriter, new ArrayList<>(), false);
}
HighlightedTextWriter writer = new HighlightedTextWriter(Configuration.getCodeFormatting(), false);
writer.appendNoHilight(super.toString());
writer.appendNoHilight(" ");
if (isInitializer) {
if (isStatic) {
writer.appendNoHilight("class initializer");
} else {
writer.appendNoHilight("instance initializer");
switch (traitsType) {
case TRAITS_TYPE_CLASS:
writer.appendNoHilight("class initializer");
break;
case TRAITS_TYPE_INSTANCE:
writer.appendNoHilight("instance initializer");
break;
case TRAITS_TYPE_SCRIPT:
writer.appendNoHilight("script initializer");
break;
default:
break;
}
} else {
if (parentTraitIndex > -1) {
if (isStatic) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
if (traitsType == TRAITS_TYPE_CLASS) {
((TraitMethodGetterSetter) abc.class_info.get(classIndex).static_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
} else {
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
((TraitMethodGetterSetter) abc.instance_info.get(classIndex).instance_traits.traits.get(parentTraitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
}
writer.appendNoHilight(" ");
}
((TraitMethodGetterSetter) traits.traits.get(traitIndex)).toStringHeader(null, convertData, "", abc, isStatic, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
((TraitMethodGetterSetter) traits.traits.get(traitIndex)).toStringHeader(null, convertData, "", abc, traitsType == TRAITS_TYPE_CLASS, ScriptExportMode.AS, -1/*FIXME*/, classIndex, writer, new ArrayList<>(), false);
}
return writer.toString();
return writer.toString().trim();
}
public int getTraitIndex() {
@@ -86,6 +94,6 @@ public abstract class MethodMultinameUsage extends TraitMultinameUsage {
}
public boolean isStatic() {
return isStatic;
return traitsType == TRAITS_TYPE_CLASS;
}
}
@@ -25,12 +25,25 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class MethodNameMultinameUsage extends MethodMultinameUsage implements DefinitionUsage {
public MethodNameMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex);
public MethodNameMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex);
}
@Override
public String toString() {
return super.toString() + " name";
}
@Override
public boolean collides(MultinameUsage other) {
if ((other instanceof MethodNameMultinameUsage) || (other instanceof ConstVarNameMultinameUsage)) {
TraitMultinameUsage otherTrait = (TraitMultinameUsage) other;
if (otherTrait.classIndex == classIndex && otherTrait.traitsType == traitsType && otherTrait.parentTraitIndex == parentTraitIndex) {
if (other.sameMultinameName(this)) {
return true;
}
}
}
return false;
}
}
@@ -25,8 +25,8 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class MethodParamsMultinameUsage extends MethodMultinameUsage {
public MethodParamsMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex);
public MethodParamsMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex);
}
@Override
@@ -25,8 +25,8 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*/
public class MethodReturnTypeMultinameUsage extends MethodMultinameUsage {
public MethodReturnTypeMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex, traitIndex, isStatic, isInitializer, traits, parentTraitIndex);
public MethodReturnTypeMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, boolean isInitializer, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, scriptIndex, classIndex, traitIndex, traitsType, isInitializer, traits, parentTraitIndex);
}
@Override
@@ -17,6 +17,10 @@
package com.jpexs.decompiler.flash.abc.usages;
import com.jpexs.decompiler.flash.abc.ABC;
import com.jpexs.decompiler.flash.abc.types.Multiname;
import com.jpexs.decompiler.flash.abc.types.Namespace;
import java.util.ArrayList;
import java.util.Objects;
/**
*
@@ -25,8 +29,61 @@ import com.jpexs.decompiler.flash.abc.ABC;
public abstract class MultinameUsage {
public ABC abc;
public int multinameIndex;
public MultinameUsage(ABC abc) {
public MultinameUsage(ABC abc, int multinameIndex) {
this.abc = abc;
this.multinameIndex = multinameIndex;
}
public int getMultinameIndex() {
return multinameIndex;
}
public ABC getAbc() {
return abc;
}
protected boolean sameMultinameName(MultinameUsage other) {
Multiname thisM = abc.constants.getMultiname(multinameIndex);
Multiname otherM = other.abc.constants.getMultiname(other.multinameIndex);
if (thisM == null && otherM == null) {
return false;
}
if (thisM == null || otherM == null) {
return false;
}
if ((thisM.kind == Multiname.QNAME || thisM.kind == Multiname.QNAMEA) && otherM.kind == thisM.kind) {
String thisName = thisM.getName(abc.constants, new ArrayList<>(), true, true);
String otherName = otherM.getName(other.abc.constants, new ArrayList<>(), true, true);
Namespace thisNs = thisM.getNamespace(abc.constants);
Namespace otherNs = otherM.getNamespace(other.abc.constants);
if (!Objects.equals(thisName, otherName)) {
return false;
}
//Both are custom namespaced
if (thisNs.kind == Namespace.KIND_NAMESPACE && otherNs.kind == Namespace.KIND_NAMESPACE) {
//compare those custom
return Objects.equals(thisNs.getName(abc.constants), otherNs.getName(other.abc.constants));
}
//One is custom namespaced, other cannot be the same
if (thisNs.kind == Namespace.KIND_NAMESPACE || otherNs.kind == Namespace.KIND_NAMESPACE) {
return false;
}
//public or package internal are colliding when have same package ns
if ((thisNs.kind == Namespace.KIND_PACKAGE || thisNs.kind == Namespace.KIND_PACKAGE_INTERNAL)
&& (otherNs.kind == Namespace.KIND_PACKAGE || otherNs.kind == Namespace.KIND_PACKAGE_INTERNAL)) {
return Objects.equals(thisNs.getName(abc.constants), otherNs.getName(other.abc.constants));
}
//one of them is private/protected
return true;
}
return false;
}
public abstract boolean collides(MultinameUsage other);
}
@@ -23,21 +23,45 @@ import com.jpexs.decompiler.flash.abc.types.traits.Traits;
*
* @author JPEXS
*/
public abstract class TraitMultinameUsage extends InsideClassMultinameUsage {
public abstract class TraitMultinameUsage extends MultinameUsage implements InsideClassMultinameUsageInterface {
public int traitIndex;
public boolean isStatic;
public static final int TRAITS_TYPE_CLASS = 1;
public static final int TRAITS_TYPE_INSTANCE = 2;
public static final int TRAITS_TYPE_SCRIPT = 3;
public int traitsType;
public int classIndex;
public int scriptIndex;
public Traits traits;
public int parentTraitIndex;
public TraitMultinameUsage(ABC abc, int multinameIndex, int classIndex, int traitIndex, boolean isStatic, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex, classIndex);
public TraitMultinameUsage(ABC abc, int multinameIndex, int scriptIndex, int classIndex, int traitIndex, int traitsType, Traits traits, int parentTraitIndex) {
super(abc, multinameIndex);
this.scriptIndex = scriptIndex;
this.classIndex = classIndex;
this.traitIndex = traitIndex;
this.isStatic = isStatic;
this.traitsType = traitsType;
this.traits = traits;
this.parentTraitIndex = parentTraitIndex;
}
@Override
public String toString() {
return "class " + abc.constants.getMultiname(abc.instance_info.get(classIndex).name_index).getNameWithNamespace(abc.constants, true).toPrintableString(true);
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
@Override
public int getClassIndex() {
return classIndex;
}
}
@@ -27,8 +27,8 @@ public class TypeNameMultinameUsage extends MultinameUsage {
public int typename_index;
public TypeNameMultinameUsage(ABC abc, int typename_index) {
super(abc);
public TypeNameMultinameUsage(ABC abc, int multinameIndex, int typename_index) {
super(abc, multinameIndex);
this.typename_index = typename_index;
}
@@ -36,4 +36,9 @@ public class TypeNameMultinameUsage extends MultinameUsage {
public String toString() {
return "TypeName " + abc.constants.getMultiname(typename_index).toString(abc.constants, new ArrayList<>());
}
@Override
public boolean collides(MultinameUsage other) {
return false;
}
}
@@ -128,7 +128,7 @@ public class AS3ScriptExporter {
if (((SetLocalAVM2Item) asg).regIndex == ((LocalRegAVM2Item) sp.object).regIndex) {
GraphTargetItem val = sp.value;
if (sp.propertyName instanceof FullMultinameAVM2Item) {
String propName = pack.abc.constants.getMultiname(((FullMultinameAVM2Item) sp.propertyName).multinameIndex).getName(pack.abc.constants, new ArrayList<>(), true);
String propName = pack.abc.constants.getMultiname(((FullMultinameAVM2Item) sp.propertyName).multinameIndex).getName(pack.abc.constants, new ArrayList<>(), true, true);
if (val instanceof CallPropertyAVM2Item) {
CallPropertyAVM2Item cap = (CallPropertyAVM2Item) val;
if (cp.propertyName instanceof FullMultinameAVM2Item) {
@@ -216,7 +216,7 @@ public class AS3ScriptExporter {
private String getTagName(ScriptPack pack, int classMIndex, int nameMindex, Map<String, String> namespaces) {
Multiname m = pack.abc.constants.getMultiname(classMIndex);
Multiname mn = pack.abc.constants.getMultiname(nameMindex);
String parentName = mn.getName(pack.abc.constants, new ArrayList<>(), true);
String parentName = mn.getName(pack.abc.constants, new ArrayList<>(), true, true);
String pkg = m.getNamespace(pack.abc.constants).getName(pack.abc.constants).toRawString();
pkg += ".*";
String ns = null;
@@ -276,7 +276,7 @@ public class AS3ScriptExporter {
if (it instanceof InitPropertyAVM2Item) {
InitPropertyAVM2Item ip = (InitPropertyAVM2Item) it;
if (ip.object instanceof ThisAVM2Item) {
String propName = pack.abc.constants.getMultiname(ip.propertyName.multinameIndex).getName(pack.abc.constants, new ArrayList<>(), true);
String propName = pack.abc.constants.getMultiname(ip.propertyName.multinameIndex).getName(pack.abc.constants, new ArrayList<>(), true, true);
GraphTargetItem val = ((InitPropertyAVM2Item) it).value;
if (val instanceof CallPropertyAVM2Item) {
CallPropertyAVM2Item cp = (CallPropertyAVM2Item) val;
@@ -296,7 +296,7 @@ public class AS3ScriptExporter {
ConstructPropAVM2Item cp = (ConstructPropAVM2Item) val;
if (cp.propertyName instanceof FullMultinameAVM2Item) {
Multiname m = pack.abc.constants.getMultiname(((FullMultinameAVM2Item) cp.propertyName).multinameIndex);
if ("mx.core.DeferredInstanceFromFunction".equals("" + m.getNameWithNamespace(pack.abc.constants))) {
if ("mx.core.DeferredInstanceFromFunction".equals("" + m.getNameWithNamespace(pack.abc.constants, true))) {
if (!cp.args.isEmpty()) {
if (cp.args.get(0) instanceof GetPropertyAVM2Item) {
GetPropertyAVM2Item gp = (GetPropertyAVM2Item) cp.args.get(0);
@@ -51,7 +51,7 @@ public class DependencyParser {
} else if ((ns.kind != Namespace.KIND_PACKAGE) && (ns.kind != Namespace.KIND_PACKAGE_INTERNAL)) {
return;
}
newimport = newimport.add(name);
newimport = newimport.addWithSuffix(name);
Dependency dep = new Dependency(newimport, dependencyType);
if (!dependencies.contains(dep)) {
@@ -80,7 +80,7 @@ public class DependencyParser {
return;
}
Namespace ns = m.getNamespace(abc.constants);
String name = m.getName(abc.constants, fullyQualifiedNames, true);
String name = m.getName(abc.constants, fullyQualifiedNames, true, true);
NamespaceSet nss = m.getNamespaceSet(abc.constants);
if (ns != null) {
parseDependenciesFromNS(ignoredCustom, abc, dependencies, uses, m.namespace_index, ignorePackage, name, dependencyType);
@@ -114,7 +114,7 @@ public class DependencyParser {
}
for (AVM2Instruction ins : body.getCode().code) {
if (ins.definition instanceof AlchemyTypeIns) {
DottedChain nimport = AlchemyTypeIns.ALCHEMY_PACKAGE.add(ins.definition.instructionName);
DottedChain nimport = AlchemyTypeIns.ALCHEMY_PACKAGE.addWithSuffix(ins.definition.instructionName);
Dependency depExp = new Dependency(nimport, DependencyType.EXPRESSION);
if (!dependencies.contains(depExp)) {
dependencies.add(depExp);
@@ -166,7 +166,7 @@ public class DependencyParser {
return;
}
Namespace ns = m.getNamespace(abc.constants);
String name = m.getName(abc.constants, fullyQualifiedNames, false);
String name = m.getName(abc.constants, fullyQualifiedNames, false, true);
NamespaceSet nss = m.getNamespaceSet(abc.constants);
if (ns != null) {
parseUsagesFromNS(ignoredCustom, abc, dependencies, uses, m.namespace_index, ignorePackage, name);
@@ -92,7 +92,7 @@ public class LinkReportExporter {
List<DottedChain> existingObjects = new ArrayList<>();
for (ScriptPack sp : as3scripts) {
existingObjects.add(sp.getClassPath().packageStr.add(sp.getClassPath().className));
existingObjects.add(sp.getClassPath().packageStr.add(sp.getClassPath().className, sp.getClassPath().namespaceSuffix));
}
for (ScriptPack sp : revList) {
@@ -119,7 +119,7 @@ public class LinkReportExporter {
ns = abc.constants.getNamespace(nss.namespaces[0]);
}
String pkgName = ns == null ? "" : ns.getName(abc.constants).toRawString();
String clsName = multiName.getName(abc.constants, new ArrayList<>(), true);
String clsName = multiName.getName(abc.constants, new ArrayList<>(), true, true);
return pkgName.isEmpty() ? clsName : pkgName + ":" + clsName;
}
@@ -167,7 +167,7 @@ public class LinkReportExporter {
sb.append(indent(3)).append("<dep id=\"AS3\" />").append(newLineChar); //Automatic
tc.getDependencies(null, abc, dependencies, uses, new DottedChain("FAKE!PACKAGE"), new ArrayList<>());
tc.getDependencies(null, abc, dependencies, uses, new DottedChain(new String[]{"FAKE!PACKAGE"}, ""), new ArrayList<>());
for (Dependency dependency : dependencies) {
DottedChain dc = dependency.getId();
if (!"*".equals(dc.getLast())) {
@@ -104,7 +104,7 @@ public class SwfToSwcExporter {
for (ScriptPack pack : packs) {
ClassPath cp = pack.getClassPath();
definedObjects.add(cp.packageStr.add(cp.className));
definedObjects.add(cp.packageStr.add(cp.className, "" /*strip*/));
}
List<ABC> allAbcList = new ArrayList<>();
@@ -123,17 +123,17 @@ public class SwfToSwcExporter {
for (ScriptPack pack : tagPacks) {
ClassPath cp = pack.getClassPath();
String defId = dottedChainToId(cp.packageStr.add(cp.className));
String defId = dottedChainToId(cp.packageStr.add(cp.className, "" /*strip*/));
sb.append(" <def id=\"").append(defId).append("\" />\n");
Set<DottedChain> allDeps = new HashSet<>();
allDeps.add(new DottedChain("AS3"));
allDeps.add(new DottedChain(new String[]{"AS3"}, ""));
sb.append(" <dep id=\"AS3\" type=\"").append(DEPENDENCY_NAMESPACE).append("\" />\n");
if (!skipDependencies) {
List<Dependency> dependencies = new ArrayList<>();
List<String> uses = new ArrayList<>();
pack.abc.script_info.get(pack.scriptIndex).traits.getDependencies(null, pack.abc, dependencies, uses, new DottedChain("NO:PACKAGE"), new ArrayList<>());
pack.abc.script_info.get(pack.scriptIndex).traits.getDependencies(null, pack.abc, dependencies, uses, new DottedChain(new String[]{"NO:PACKAGE"}, ""), new ArrayList<>());
for (Dependency d : dependencies) {
if ("*".equals(d.getId().getLast())) {
@@ -86,11 +86,11 @@ public class MxmlcAs3ScriptReplacer extends MxmlcRunner implements As3ScriptRepl
if (ii.deleted) {
return true;
}
if (ii.super_index != 0 && isParentDeleted(abc, allAbcs, abc.constants.getMultiname(ii.super_index).getNameWithNamespace(abc.constants))) {
if (ii.super_index != 0 && isParentDeleted(abc, allAbcs, abc.constants.getMultiname(ii.super_index).getNameWithNamespace(abc.constants, false))) {
return true;
}
for (int iface : ii.interfaces) {
if (isParentDeleted(abc, allAbcs, abc.constants.getMultiname(iface).getNameWithNamespace(abc.constants))) {
if (isParentDeleted(abc, allAbcs, abc.constants.getMultiname(iface).getNameWithNamespace(abc.constants, false))) {
return true;
}
}
@@ -265,7 +265,7 @@ public class MxmlcAs3ScriptReplacer extends MxmlcRunner implements As3ScriptRepl
//remove all subclasses from the SWC
for (ScriptPack sp : copyPacks) {
DottedChain dc = sp.getPathPackage().add(sp.getPathScriptName());
DottedChain dc = sp.getPathPackage().add(sp.getPathScriptName(), "");
if (isParentDeleted(sp.abc, sp.allABCs, dc)) {
sp.abc.script_info.get(sp.scriptIndex).delete(sp.abc, true);
modAbcs.add(sp.abc);
@@ -18,6 +18,7 @@ package com.jpexs.decompiler.flash.timeline;
import com.jpexs.decompiler.flash.IdentifiersDeobfuscation;
import com.jpexs.decompiler.flash.SWF;
import com.jpexs.decompiler.flash.abc.ClassPath;
import com.jpexs.decompiler.flash.abc.ScriptPack;
import com.jpexs.decompiler.flash.treeitems.AS3ClassTreeItem;
import java.util.ArrayList;
@@ -44,7 +45,7 @@ public class AS3Package extends AS3ClassTreeItem {
private List<ScriptPack> sortedScripts;
public AS3Package(String packageName, SWF swf) {
super(packageName, null);
super(packageName, "", null);
this.swf = swf;
this.packageName = packageName;
}
@@ -81,12 +82,13 @@ public class AS3Package extends AS3ClassTreeItem {
}
public void addScriptPack(ScriptPack script) {
scripts.put(script.getClassPath().className, script);
ClassPath cp = script.getClassPath();
scripts.put(cp.className + cp.namespaceSuffix, script);
sortedScripts = null;
}
public void addSubPackage(AS3Package subPackage) {
subPackages.put(subPackage.getName(), subPackage);
subPackages.put(subPackage.getNameWithNamespaceSuffix(), subPackage);
sortedPackages = null;
}
@@ -29,13 +29,20 @@ public abstract class AS3ClassTreeItem implements TreeItem {
private final ClassPath path;
public AS3ClassTreeItem(String name, ClassPath path) {
private final String namespaceSuffix;
public AS3ClassTreeItem(String name, String namespaceSuffix, ClassPath path) {
this.name = name;
this.path = path;
this.namespaceSuffix = namespaceSuffix;
}
public String getName() {
return name;
public String getNameWithNamespaceSuffix() {
String ret = name;
if (namespaceSuffix != null) {
ret += namespaceSuffix;
}
return ret;
}
public String getPath() {
@@ -44,6 +51,10 @@ public abstract class AS3ClassTreeItem implements TreeItem {
@Override
public String toString() {
return IdentifiersDeobfuscation.printIdentifier(true, name);
String ret = IdentifiersDeobfuscation.printIdentifier(true, name);
if (namespaceSuffix != null) {
ret += namespaceSuffix;
}
return ret;
}
}
@@ -30,37 +30,39 @@ import java.util.List;
*/
public class DottedChain implements Serializable, Comparable<DottedChain> {
public static final String NO_SUFFIX = "";
public static final DottedChain EMPTY = new DottedChain(true);
public static final DottedChain TOPLEVEL = new DottedChain();
public static final DottedChain TOPLEVEL = new DottedChain(new String[]{}, NO_SUFFIX);
public static final DottedChain BOOLEAN = new DottedChain("Boolean");
public static final DottedChain BOOLEAN = new DottedChain(new String[]{"Boolean"}, NO_SUFFIX);
public static final DottedChain STRING = new DottedChain("String");
public static final DottedChain STRING = new DottedChain(new String[]{"String"}, NO_SUFFIX);
public static final DottedChain ARRAY = new DottedChain("Array");
public static final DottedChain ARRAY = new DottedChain(new String[]{"Array"}, NO_SUFFIX);
public static final DottedChain NUMBER = new DottedChain("Number");
public static final DottedChain NUMBER = new DottedChain(new String[]{"Number"}, NO_SUFFIX);
public static final DottedChain OBJECT = new DottedChain("Object");
public static final DottedChain OBJECT = new DottedChain(new String[]{"Object"}, NO_SUFFIX);
public static final DottedChain INT = new DottedChain("int");
public static final DottedChain INT = new DottedChain(new String[]{"int"}, NO_SUFFIX);
public static final DottedChain UINT = new DottedChain("uint");
public static final DottedChain UINT = new DottedChain(new String[]{"uint"}, NO_SUFFIX);
public static final DottedChain UNDEFINED = new DottedChain("Undefined");
public static final DottedChain UNDEFINED = new DottedChain(new String[]{"Undefined"}, NO_SUFFIX);
public static final DottedChain XML = new DottedChain("XML");
public static final DottedChain XML = new DottedChain(new String[]{"XML"}, NO_SUFFIX);
public static final DottedChain NULL = new DottedChain("null");
public static final DottedChain NULL = new DottedChain(new String[]{"null"}, NO_SUFFIX);
public static final DottedChain FUNCTION = new DottedChain("Function");
public static final DottedChain FUNCTION = new DottedChain(new String[]{"Function"}, NO_SUFFIX);
public static final DottedChain VOID = new DottedChain("void");
public static final DottedChain VOID = new DottedChain(new String[]{"void"}, NO_SUFFIX);
public static final DottedChain NAMESPACE = new DottedChain("Namespace");
public static final DottedChain NAMESPACE = new DottedChain(new String[]{"Namespace"}, NO_SUFFIX);
public static final DottedChain ALL = new DottedChain("*");
public static final DottedChain ALL = new DottedChain(new String[]{"*"}, NO_SUFFIX);
private final String[] parts;
@@ -70,13 +72,25 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
private boolean isNull = false;
public static final DottedChain parse(String name) {
private String namespaceSuffix = "";
public String getNamespaceSuffix() {
return namespaceSuffix;
}
public static final DottedChain parseWithSuffix(String name) {
if (name == null) {
return DottedChain.EMPTY;
} else if (name.isEmpty()) {
return DottedChain.TOPLEVEL;
} else {
return new DottedChain(name.split("\\."));
String nameNoSuffix = name;
String namespaceSuffix = "";
if (name.matches(".*#[0-9]+$")) {
nameNoSuffix = name.substring(0, name.lastIndexOf("#"));
namespaceSuffix = name.substring(name.lastIndexOf("#"));
}
return new DottedChain(nameNoSuffix.split("\\."), namespaceSuffix);
}
}
@@ -88,7 +102,7 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
}
public DottedChain(DottedChain src) {
this(src.parts);
this(src.parts, src.namespaceSuffix);
this.isNull = src.isNull;
}
@@ -98,7 +112,10 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
hash = calcHash();
}
public DottedChain(String... parts) {
/*public DottedChain(String onePart, String namespaceSuffix) {
this(new String[]{onePart}, namespaceSuffix);
}*/
public DottedChain(String[] parts, String namespaceSuffix) {
if (parts.length == 1 && parts[0].isEmpty()) {
length = 0;
this.parts = new String[0];
@@ -107,6 +124,7 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
this.parts = parts;
}
hash = calcHash();
this.namespaceSuffix = namespaceSuffix;
}
private DottedChain(String[] parts, int length) {
@@ -165,7 +183,17 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
return new DottedChain(parts, length - 1);
}
public DottedChain add(String name) {
public DottedChain addWithSuffix(String name) {
String addedNameNoSuffix = name;
String addedNamespaceSuffix = "";
if (name != null && name.matches(".*#[0-9]+$")) {
addedNameNoSuffix = name.substring(0, name.lastIndexOf("#"));
addedNamespaceSuffix = name.substring(name.lastIndexOf("#"));
}
return add(addedNameNoSuffix, addedNamespaceSuffix);
}
public DottedChain add(String name, String namespaceSuffix) {
if (name == null) {
return new DottedChain(this);
}
@@ -175,10 +203,10 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
}
nparts[nparts.length - 1] = name;
return new DottedChain(nparts);
return new DottedChain(nparts, namespaceSuffix);
}
protected String toString(boolean as3, boolean raw) {
protected String toString(boolean as3, boolean raw, boolean withSuffix) {
if (isNull) {
return "";
}
@@ -196,6 +224,9 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
boolean lastStar = i == length - 1 && "*".equals(part);
ret.append((raw || lastStar) ? part : IdentifiersDeobfuscation.printIdentifier(as3, part));
}
if (withSuffix) {
ret.append(namespaceSuffix);
}
return ret.toString();
}
@@ -223,11 +254,11 @@ public class DottedChain implements Serializable, Comparable<DottedChain> {
}
public String toPrintableString(boolean as3) {
return toString(as3, false);
return toString(as3, false, true);
}
public String toRawString() {
return toString(false/*ignored*/, true);
public String toRawString() { //Is SUFFIX correctly handled?
return toString(false/*ignored*/, true, true);
}
@Override
@@ -43,7 +43,7 @@ public class TypeItem extends GraphTargetItem {
public final DottedChain fullTypeName;
public TypeItem(String s) {
this(s == null ? new DottedChain() : new DottedChain(s.split("\\.")));
this(s == null ? new DottedChain(new String[]{}, "") : DottedChain.parseWithSuffix(s));
}
public TypeItem(DottedChain fullTypeName) {
@@ -78,7 +78,7 @@ public class TypeItem extends GraphTargetItem {
public GraphTextWriter appendTo(GraphTextWriter writer, LocalData localData) throws InterruptedException {
boolean as3 = localData.constantsAvm2 != null;
if (localData.fullyQualifiedNames.contains(new DottedChain(fullTypeName.getLast()))) {
if (localData.fullyQualifiedNames.contains(DottedChain.parseWithSuffix(fullTypeName.getLast()))) {
writer.hilightSpecial(fullTypeName.toPrintableString(as3), HighlightSpecialType.TYPE_NAME, fullTypeName.toRawString());
} else {
writer.hilightSpecial(IdentifiersDeobfuscation.printIdentifier(as3, fullTypeName.getLast()), HighlightSpecialType.TYPE_NAME, fullTypeName.toRawString());
@@ -66,7 +66,7 @@ public class ActionScript3Test extends ActionScriptTestBase {
}
}
assertNotNull(tag);
clsIndex = tag.getABC().findClassByName(new DottedChain("classes", "Test"));
clsIndex = tag.getABC().findClassByName(new DottedChain(new String[]{"classes", "Test"}, ""));
assertTrue(clsIndex > -1);
this.abc = tag.getABC();
Configuration.autoDeobfuscate.set(false);
@@ -55,12 +55,16 @@ public class AS3Generator {
break;
}
}
if (tag == null) {
System.err.println("No ABC found");
return;
}
ABC abc = tag.getABC();
int classId = abc.findClassByName("classes.Test");
StringBuilder s = new StringBuilder();
for (Trait t : abc.instance_info.get(classId).instance_traits.traits) {
if (t instanceof TraitMethodGetterSetter) {
String name = t.getName(abc).getName(abc.constants, null, true);
String name = t.getName(abc).getName(abc.constants, null, true, true);
if (name.startsWith("test")) {
s.append("@Test\r\npublic void ");
s.append(name);
+25
View File
@@ -0,0 +1,25 @@
package {
import flash.display.Sprite;
import flash.text.TextField;
import flash.utils.ByteArray;
public class EmptyDocument extends Sprite{
public var attr:int = 5;
public function EmptyDocument() {
var mc:MyClass = new MyClass();
var mc2:MyClass2 = new MyClass2()
var r = mc.getResult() + mc2.getResult();
var expected = 561;
var display_txt:TextField = new TextField();
display_txt.text = "Actual = "+r+", expected = "+expected+", "+(r==expected?"OKAY":"FAIL");
display_txt.width = 300;
addChild(display_txt);
}
}
}
+114
View File
@@ -0,0 +1,114 @@
package {
public class MyClass {
public var a1:int = 1;
public var a2:int = 2;
private var a1x:int = 3;
private var a2x:int = 4;
protected var a1y:int = 5;
protected var a2y:int = 6;
public static var a1:int = 7;
public static var a2:int = 8;
private static var a1x:int = 9;
private static var a2x:int = 10;
protected static var a1y:int = 11;
protected static var a2y:int = 12;
myns var a1:int = 13;
myns var a2:int = 14;
myns2 var a1:int = 15;
myns2 var a2:int = 16;
public function f1():int {
return 17;
}
public function f2():int {
return 18;
}
protected function f1x():int {
return 19;
}
protected function f2x():int {
return 20;
}
private function f1y():int {
return 21;
}
private function f2y():int {
return 22;
}
public static function f1():int {
return 23;
}
public static function f2():int {
return 24;
}
protected static function f1x():int {
return 25;
}
protected static function f2x():int {
return 26;
}
private static function f1y():int {
return 27;
}
private static function f2y():int {
return 28;
}
myns function f1():int {
return 29;
}
myns function f2():int {
return 30;
}
myns2 function f1():int {
return 31;
}
myns2 function f2():int {
return 32;
}
public function getResult():int {
var inst_a = this.a1 + this.a2 + this.a1x + this.a2x + this.a1y + this.a2y;
var inst_f = this.f1() + this.f2() + this.f1x() + this.f2x() + this.f1y() + this.f2y();
var inst = inst_a + inst_f;
var stat_a = MyClass.a1 + MyClass.a2 + MyClass.a1x + MyClass.a2x + MyClass.a1y + MyClass.a2y;
var stat_f = MyClass.f1() + MyClass.f2() + MyClass.f1x() + MyClass.f2x() + MyClass.f1y() + MyClass.f2y();
var stat = stat_a + stat_f;
var ns_a = myns::a1 + myns::a2 + myns2::a1 + myns2::a2;
var ns_f = myns::f1() + myns::f2() + myns2::f1() + myns2::f2();
var ns = ns_a + ns_f;
return inst+stat+ns; //528
}
}
}
+15
View File
@@ -0,0 +1,15 @@
package {
public class MyClass2 {
public function MyClass2() {
}
public function getResult():int{
return 33;
}
}
}
+5
View File
@@ -0,0 +1,5 @@
package {
public namespace myns = "http://www.example.com";
}
+5
View File
@@ -0,0 +1,5 @@
package {
public namespace myns2 = "http://www.example2.com";
}
Binary file not shown.
+49
View File
@@ -0,0 +1,49 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en">
<head>
<title>namespaces</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<style type="text/css" media="screen">
html, body { height:100%; background-color: #ffffff;}
body { margin:0; padding:0; overflow:hidden; }
#flashContent { width:100%; height:100%; }
</style>
</head>
<body>
<div id="flashContent">
<object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" width="550" height="400" id="namespaces" align="middle">
<param name="movie" value="namespaces.swf" />
<param name="quality" value="high" />
<param name="bgcolor" value="#ffffff" />
<param name="play" value="true" />
<param name="loop" value="true" />
<param name="wmode" value="window" />
<param name="scale" value="showall" />
<param name="menu" value="true" />
<param name="devicefont" value="false" />
<param name="salign" value="" />
<param name="allowScriptAccess" value="sameDomain" />
<!--[if !IE]>-->
<object type="application/x-shockwave-flash" data="namespaces.swf" width="550" height="400">
<param name="movie" value="namespaces.swf" />
<param name="quality" value="high" />
<param name="bgcolor" value="#ffffff" />
<param name="play" value="true" />
<param name="loop" value="true" />
<param name="wmode" value="window" />
<param name="scale" value="showall" />
<param name="menu" value="true" />
<param name="devicefont" value="false" />
<param name="salign" value="" />
<param name="allowScriptAccess" value="sameDomain" />
<!--<![endif]-->
<a href="http://www.adobe.com/go/getflash">
<img src="http://www.adobe.com/images/shared/download_buttons/get_flash_player.gif" alt="Get Adobe Flash player" />
</a>
<!--[if !IE]>-->
</object>
<!--<![endif]-->
</object>
</div>
</body>
</html>
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -110,6 +110,8 @@ SingleCharacter = [^\r\n\'\\]
OIdentifierCharacter = [^\r\n\u00A7\\]
Preprocessor = \u00A7\u00A7 {Identifier}
NamespaceSuffix = "#" {DecIntegerLiteral}
RegExp = \/([^\r\n/]|\\\/)+\/[a-z]*
%state STRING, CHARLITERAL, XMLSTARTTAG, XML, OIDENTIFIER
@@ -289,7 +291,9 @@ RegExp = \/([^\r\n/]|\\\/)+\/[a-z]*
xmlTagName = s.substring(1);
}*/
/* identifiers */
{Identifier}{NamespaceSuffix} { return token(TokenType.REGEX); }
{Identifier} { return token(TokenType.IDENTIFIER); }
}
<XMLSTARTTAG> {
@@ -328,6 +332,12 @@ RegExp = \/([^\r\n/]|\\\/)+\/[a-z]*
}
<OIDENTIFIER> {
"\u00A7" {NamespaceSuffix} {
yybegin(YYINITIAL);
// length also includes the trailing quote + namespace suffix
return token(TokenType.REGEX, tokenStart, tokenLength + yylength());
}
"\u00A7" {
yybegin(YYINITIAL);
// length also includes the trailing quote
@@ -3749,7 +3749,7 @@ public class CommandLineArgumentParser {
String dcs = swf.getDocumentClass();
if (dcs != null) {
if (dcs.contains(".")) {
DottedChain dc = new DottedChain(dcs.split("\\."));
DottedChain dc = DottedChain.parseWithSuffix(dcs);
pw.println("documentClass=" + dc.toPrintableString(true));
} else {
pw.println("documentClass=" + IdentifiersDeobfuscation.printIdentifier(true, dcs));
@@ -571,7 +571,7 @@ public class DebuggerHandler implements DebugConnectionListener {
Matcher m;
if ((m = patAS3.matcher(name)).matches()) {
String clsName = m.group(3);
String clsNameWithSuffix = m.group(3);
String pkg = m.group(2).replace("\\", ".");
m = patAS3PCode.matcher(name);
@@ -579,10 +579,10 @@ public class DebuggerHandler implements DebugConnectionListener {
moduleToClassIndex.put(file, Integer.parseInt(m.group(3)));
moduleToTraitIndex.put(file, Integer.parseInt(m.group(4)));
moduleToMethodIndex.put(file, Integer.parseInt(m.group(5)));
name = DottedChain.parse(pkg).add(clsName).toString();
name = DottedChain.parseWithSuffix(pkg).addWithSuffix(clsNameWithSuffix).toString();
name = "#PCODE abc:" + m.group(1) + ",body:" + m.group(6) + ";" + name;
} else {
name = DottedChain.parse(pkg).add(clsName).toString();
name = DottedChain.parseWithSuffix(pkg).addWithSuffix(clsNameWithSuffix).toString();
}
}
modulePaths.put(file, name);
@@ -357,6 +357,14 @@ public abstract class MainFrameMenu implements MenuBuilder {
mainFrame.getPanel().renameOneIdentifier(swf);
}
protected void renameColliding(ActionEvent evt) {
if (Main.isWorking()) {
return;
}
mainFrame.getPanel().renameColliding(swf);
}
protected void renameInvalidIdentifiers(ActionEvent evt) {
if (Main.isWorking()) {
return;
@@ -718,6 +726,7 @@ public abstract class MainFrameMenu implements MenuBuilder {
setMenuEnabled("/tools/deobfuscation", swfSelected);
setMenuEnabled("/tools/deobfuscation/renameOneIdentifier", swfSelected && !isWorking);
setMenuEnabled("/tools/deobfuscation/renameInvalidIdentifiers", swfSelected && !isWorking);
setMenuEnabled("/tools/deobfuscation/renameColliding", swfSelected && !isWorking);
setMenuEnabled("/tools/deobfuscation/deobfuscation", hasAbc);
setMenuEnabled("/tools/search", swfSelected);
@@ -889,6 +898,7 @@ public abstract class MainFrameMenu implements MenuBuilder {
addMenuItem("/tools/deobfuscation", translate("menu.tools.deobfuscation"), "deobfuscate16", null, 0, null, false, null, false);
addMenuItem("/tools/deobfuscation/renameOneIdentifier", translate("menu.tools.deobfuscation.globalrename"), "rename16", this::renameOneIdentifier, PRIORITY_MEDIUM, null, true, null, false);
addMenuItem("/tools/deobfuscation/renameInvalidIdentifiers", translate("menu.tools.deobfuscation.renameinvalid"), "renameall16", this::renameInvalidIdentifiers, PRIORITY_MEDIUM, null, true, null, false);
addMenuItem("/tools/deobfuscation/renameColliding", translate("menu.tools.deobfuscation.renameColliding"), "renameall16", this::renameColliding, PRIORITY_MEDIUM, null, true, null, false);
addMenuItem("/tools/deobfuscation/deobfuscation", translate("menu.tools.deobfuscation.pcode"), "deobfuscate32", this::deobfuscationActionPerformed, PRIORITY_TOP, null, true, null, false);
finishMenu("/tools/deobfuscation");
@@ -27,6 +27,7 @@ import com.jpexs.decompiler.flash.abc.ABC;
import com.jpexs.decompiler.flash.abc.RenameType;
import com.jpexs.decompiler.flash.abc.ScriptPack;
import com.jpexs.decompiler.flash.abc.avm2.AVM2ConstantPool;
import com.jpexs.decompiler.flash.abc.avm2.deobfuscation.AbcMultiNameCollisionFixer;
import com.jpexs.decompiler.flash.abc.avm2.deobfuscation.DeobfuscationLevel;
import com.jpexs.decompiler.flash.abc.types.traits.Trait;
import com.jpexs.decompiler.flash.configuration.Configuration;
@@ -1913,6 +1914,48 @@ public final class MainPanel extends JPanel implements TreeSelectionListener, Se
updateClassesList();
}
public void renameColliding(final SWF swf) {
if (swf == null) {
return;
}
if (confirmExperimental()) {
new CancellableWorker<Integer>() {
@Override
protected Integer doInBackground() throws Exception {
AbcMultiNameCollisionFixer fixer = new AbcMultiNameCollisionFixer();
return fixer.fixCollisions(swf);
}
@Override
protected void onStart() {
Main.startWork(translate("work.renaming.identifiers") + "...", this);
}
@Override
protected void done() {
View.execInEventDispatch(() -> {
try {
int cnt = get();
Main.stopWork();
View.showMessageDialog(null, translate("message.rename.renamed").replace("%count%", Integer.toString(cnt)));
swf.assignClassesToSymbols();
swf.clearScriptCache();
if (abcPanel != null) {
abcPanel.reload();
}
updateClassesList();
reload(true);
} catch (Exception ex) {
logger.log(Level.SEVERE, "Error during renaming identifiers", ex);
Main.stopWork();
View.showMessageDialog(null, translate("error.occured").replace("%error%", ex.getClass().getSimpleName()));
}
});
}
}.execute();
}
}
public void renameOneIdentifier(final SWF swf) {
if (swf == null) {
return;
@@ -213,7 +213,7 @@ public class ABCPanel extends JPanel implements ItemListener, SearchListener<ABC
continue;
}
if (Configuration._ignoreAdditionalFlexClasses.get()) {
String fullName = pack.getClassPath().packageStr.add(pack.getClassPath().className).toRawString();
String fullName = pack.getClassPath().packageStr.add(pack.getClassPath().className, pack.getClassPath().namespaceSuffix).toRawString();
if (ignoredClasses.contains(fullName)) {
continue;
}
@@ -1048,7 +1048,10 @@ public class ABCPanel extends JPanel implements ItemListener, SearchListener<ABC
return false; //?
}
SyntaxDocument sd = (SyntaxDocument) decompiledTextArea.getDocument();
Token t = sd.getTokenAt(pos + 1);
Token currentChartoken = sd.getTokenAt(pos);
Token nextChartoken = sd.getTokenAt(pos + 1);
Token t = currentChartoken != null && currentChartoken.length == 1 ? currentChartoken : nextChartoken;
if (t == null || (t.type != TokenType.IDENTIFIER && t.type != TokenType.KEYWORD && t.type != TokenType.REGEX)) {
return false;
}
@@ -1102,7 +1105,7 @@ public class ABCPanel extends JPanel implements ItemListener, SearchListener<ABC
Reference<Integer> multinameIndexRef = new Reference<>(0);
if (decompiledTextArea.getPropertyTypeAtPos(pos, abcIndex, classIndex, traitIndex, classTrait, multinameIndexRef)) {
UsageFrame.gotoUsage(ABCPanel.this, new TraitMultinameUsage(getAbcList().get(abcIndex.getVal()).getABC(), multinameIndexRef.getVal(), classIndex.getVal(), traitIndex.getVal(), classTrait.getVal(), null, -1) {
UsageFrame.gotoUsage(ABCPanel.this, new TraitMultinameUsage(getAbcList().get(abcIndex.getVal()).getABC(), multinameIndexRef.getVal(), decompiledTextArea.getScriptLeaf().scriptIndex, classIndex.getVal(), traitIndex.getVal(), classTrait.getVal() ? TraitMultinameUsage.TRAITS_TYPE_CLASS : TraitMultinameUsage.TRAITS_TYPE_INSTANCE, null, -1) {
});
return;
}
@@ -1244,7 +1247,7 @@ public class ABCPanel extends JPanel implements ItemListener, SearchListener<ABC
ClassPath classPath = item.getClassPath();
// first check the className to avoid calling unnecessary toString
if (name.endsWith(classPath.className) && classPath.toRawString().equals(name)) {
if (name.endsWith(classPath.className + classPath.namespaceSuffix) && classPath.toRawString().equals(name)) {
pack = item;
break;
}
@@ -51,7 +51,7 @@ public class ClassesListTreeModel extends AS3ClassTreeItem implements TreeModel
}
public ClassesListTreeModel(SWF swf) {
super(null, null);
super(null, null, null);
root = new AS3Package(null, swf);
this.swf = swf;
this.list = swf.getAS3Packs();
@@ -92,7 +92,7 @@ public class ClassesListTreeModel extends AS3ClassTreeItem implements TreeModel
continue;
}
if (Configuration._ignoreAdditionalFlexClasses.get()) {
String fullName = item.getClassPath().packageStr.add(item.getClassPath().className).toRawString();
String fullName = item.getClassPath().packageStr.add(item.getClassPath().className, item.getClassPath().namespaceSuffix).toRawString();
if (ignoredClasses.contains(fullName)) {
continue;
}
@@ -282,7 +282,7 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
Highlighting ch = Highlighting.searchPos(classHighlights, pos);
int cindex = (int) ch.getProperties().index;
ABC abc = getABC();
type.setVal(abc.instance_info.get(cindex).getName(abc.constants).getNameWithNamespace(abc.constants));
type.setVal(abc.instance_info.get(cindex).getName(abc.constants).getNameWithNamespace(abc.constants, true));
return ch.startPos;
}
@@ -333,7 +333,7 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
break;
}
}
if (t.type != TokenType.IDENTIFIER && t.type != TokenType.KEYWORD || t.type == TokenType.REGEX) {
if (t.type != TokenType.IDENTIFIER && t.type != TokenType.KEYWORD && t.type != TokenType.REGEX) {
return false;
}
Reference<DottedChain> locTypeRef = new Reference<>(DottedChain.EMPTY);
@@ -343,9 +343,8 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
return false;
}
boolean found;
t = sd.getNextToken(t);
while (t != lastToken && !currentType.equals(DottedChain.ALL)) {
t = sd.getNextToken(t);
while (!currentType.equals(DottedChain.ALL)) {
String ident = t.getString(sd);
found = false;
List<ABCContainerTag> abcList = getABC().getSwf().getAbcList();
@@ -357,13 +356,13 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
InstanceInfo ii = a.instance_info.get(cindex);
for (int j = 0; j < ii.instance_traits.traits.size(); j++) {
Trait tr = ii.instance_traits.traits.get(j);
if (ident.equals(tr.getName(a).getName(a.constants, null, false /*NOT RAW!*/))) {
if (ident.equals(tr.getName(a).getName(a.constants, null, false /*NOT RAW!*/, true))) {
classIndex.setVal(cindex);
abcIndex.setVal(i);
traitIndex.setVal(j);
classTrait.setVal(false);
multinameIndex.setVal(tr.name_index);
currentType = ii.getName(a.constants).getNameWithNamespace(a.constants);
currentType = ii.getName(a.constants).getNameWithNamespace(a.constants, true);
found = true;
break loopi;
}
@@ -372,13 +371,13 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
ClassInfo ci = a.class_info.get(cindex);
for (int j = 0; j < ci.static_traits.traits.size(); j++) {
Trait tr = ci.static_traits.traits.get(j);
if (ident.equals(tr.getName(a).getName(a.constants, null, false /*NOT RAW!*/))) {
if (ident.equals(tr.getName(a).getName(a.constants, null, false /*NOT RAW!*/, true))) {
classIndex.setVal(cindex);
abcIndex.setVal(i);
traitIndex.setVal(j);
classTrait.setVal(true);
multinameIndex.setVal(tr.name_index);
currentType = ii.getName(a.constants).getNameWithNamespace(a.constants);
currentType = ii.getName(a.constants).getNameWithNamespace(a.constants, true);
found = true;
break loopi;
}
@@ -389,10 +388,14 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
return false;
}
if (t == lastToken) {
break;
}
t = sd.getNextToken(t);
if (!".".equals(t.getString(sd))) {
break;
}
t = sd.getNextToken(t);
}
return true;
}
@@ -481,7 +484,7 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
for (int i = 1; i < abc.constants.getMultinameCount(); i++) {
Multiname m = abc.constants.getMultiname(i);
if (m != null) {
if (typeName.equals(m.getNameWithNamespace(abc.constants).toRawString())) {
if (typeName.equals(m.getNameWithNamespace(abc.constants, true).toRawString())) {
return i;
}
}
@@ -536,7 +539,7 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
if (tm != null) {
String name = "";
if (classIndex > -1) {
name = abc.instance_info.get(classIndex).getName(abc.constants).getNameWithNamespace(abc.constants).toPrintableString(true);
name = abc.instance_info.get(classIndex).getName(abc.constants).getNameWithNamespace(abc.constants, true).toPrintableString(true);
}
Trait currentTrait = null;
@@ -547,7 +550,7 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
currentTrait = getCurrentTrait();
isStatic = abc.isStaticTraitId(classIndex, lastTraitIndex);
if (currentTrait != null) {
name += ":" + currentTrait.getName(abc).getName(abc.constants, null, false);
name += ":" + currentTrait.getName(abc).getName(abc.constants, null, false, true);
}
}
}
@@ -588,11 +591,11 @@ public class DecompiledEditorPane extends DebuggableEditorPane implements CaretL
}
currentMethodHighlight = null;
//currentTrait = null;
String name = abc.instance_info.get(classIndex).getName(abc.constants).getNameWithNamespace(abc.constants).toPrintableString(true);
String name = abc.instance_info.get(classIndex).getName(abc.constants).getNameWithNamespace(abc.constants, true).toPrintableString(true);
currentTrait = getCurrentTrait();
isStatic = abc.isStaticTraitId(classIndex, lastTraitIndex);
if (currentTrait != null) {
name += ":" + currentTrait.getName(abc).getName(abc.constants, null, false);
name += ":" + currentTrait.getName(abc).getName(abc.constants, null, false, true);
}
displayMethod(pos, abc.findMethodIdByTraitId(classIndex, lastTraitIndex), name, currentTrait, lastTraitIndex, isStatic);
@@ -286,7 +286,7 @@ public class DetailPanel extends JPanel implements TagEditorPanel {
if (trait == null) {
traitNameLabel.setText("-");
} else if (abcPanel != null) {
traitNameLabel.setText(trait.getName(abcPanel.abc).getName(abcPanel.abc.constants, null, false));
traitNameLabel.setText(trait.getName(abcPanel.abc).getName(abcPanel.abc.constants, null, false, true));
}
});
@@ -123,6 +123,7 @@ public class SlotConstTraitDetailPanel extends JPanel implements TraitDetail {
return false;
}
abc.refreshMultinameNamespaceSuffixes();
((Tag) abc.parentTag).setModified(true);
return true;
}
@@ -97,9 +97,9 @@ public class TraitsListItem {
return "__" + STR_SCRIPT_INITIALIZER;
}
if (isStatic) {
return abc.class_info.get(classIndex).static_traits.traits.get(index).getName(abc).getName(abc.constants, null, false);
return abc.class_info.get(classIndex).static_traits.traits.get(index).getName(abc).getName(abc.constants, null, false, true);
} else {
return abc.instance_info.get(classIndex).instance_traits.traits.get(index).getName(abc).getName(abc.constants, null, false);
return abc.instance_info.get(classIndex).instance_traits.traits.get(index).getName(abc).getName(abc.constants, null, false, true);
}
}
@@ -19,7 +19,7 @@ package com.jpexs.decompiler.flash.gui.abc;
import com.jpexs.decompiler.flash.abc.ABC;
import com.jpexs.decompiler.flash.abc.types.Multiname;
import com.jpexs.decompiler.flash.abc.types.Namespace;
import com.jpexs.decompiler.flash.abc.usages.InsideClassMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.InsideClassMultinameUsageInterface;
import com.jpexs.decompiler.flash.abc.usages.MethodMultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.MultinameUsage;
import com.jpexs.decompiler.flash.abc.usages.TraitMultinameUsage;
@@ -92,21 +92,21 @@ public class UsageFrame extends AppDialog implements MouseListener {
cont.add(new JScrollPane(usageList), BorderLayout.CENTER);
cont.add(buttonsPanel, BorderLayout.SOUTH);
setSize(400, 300);
setTitle((definitions ? translate("dialog.title.declaration") : translate("dialog.title")) + abc.constants.getMultiname(multinameIndex).getNameWithNamespace(abc.constants).toPrintableString(true));
setTitle((definitions ? translate("dialog.title.declaration") : translate("dialog.title")) + abc.constants.getMultiname(multinameIndex).getNameWithNamespace(abc.constants, true).toPrintableString(true));
View.centerScreen(this);
View.setWindowIcon(this);
}
public static void gotoUsage(final ABCPanel abcPanel, final MultinameUsage usage) {
if (usage instanceof InsideClassMultinameUsage) {
final InsideClassMultinameUsage icu = (InsideClassMultinameUsage) usage;
if (usage instanceof InsideClassMultinameUsageInterface) {
final InsideClassMultinameUsageInterface icu = (InsideClassMultinameUsageInterface) usage;
Runnable settrait = new Runnable() {
@Override
public void run() {
abcPanel.decompiledTextArea.removeScriptListener(this);
abcPanel.decompiledTextArea.setClassIndex(icu.classIndex);
abcPanel.decompiledTextArea.setClassIndex(icu.getClassIndex());
if (usage instanceof TraitMultinameUsage) {
TraitMultinameUsage tmu = (TraitMultinameUsage) usage;
int traitIndex;
@@ -115,13 +115,13 @@ public class UsageFrame extends AppDialog implements MouseListener {
} else {
traitIndex = tmu.traitIndex;
}
if (!tmu.isStatic) {
if (tmu.traitsType == TraitMultinameUsage.TRAITS_TYPE_INSTANCE) {
traitIndex += abcPanel.abc.class_info.get(tmu.classIndex).static_traits.traits.size();
}
if (tmu instanceof MethodMultinameUsage) {
MethodMultinameUsage mmu = (MethodMultinameUsage) usage;
if (mmu.isInitializer == true) {
traitIndex = abcPanel.abc.class_info.get(mmu.classIndex).static_traits.traits.size() + abcPanel.abc.instance_info.get(mmu.classIndex).instance_traits.traits.size() + (mmu.isStatic ? 1 : 0);
traitIndex = abcPanel.abc.class_info.get(mmu.classIndex).static_traits.traits.size() + abcPanel.abc.instance_info.get(mmu.classIndex).instance_traits.traits.size() + (mmu.traitsType == TraitMultinameUsage.TRAITS_TYPE_CLASS ? 1 : 0);
}
}
abcPanel.decompiledTextArea.gotoTrait(traitIndex);
@@ -129,11 +129,11 @@ public class UsageFrame extends AppDialog implements MouseListener {
}
};
if (abcPanel.decompiledTextArea.getClassIndex() == icu.classIndex && abcPanel.abc == icu.abc) {
if (abcPanel.decompiledTextArea.getClassIndex() == icu.getClassIndex() && abcPanel.abc == icu.getAbc()) {
settrait.run();
} else {
abcPanel.decompiledTextArea.addScriptListener(settrait);
abcPanel.hilightScript(abcPanel.getSwf(), icu.abc.instance_info.get(icu.classIndex).getName(icu.abc.constants).getNameWithNamespace(icu.abc.constants).toRawString());
abcPanel.hilightScript(abcPanel.getSwf(), icu.getAbc().instance_info.get(icu.getClassIndex()).getName(icu.getAbc().constants).getNameWithNamespace(icu.getAbc().constants, true).toRawString());
}
}
}

Some files were not shown because too many files have changed in this diff Show More