diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/instructions/other/GetPropertyIns.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/instructions/other/GetPropertyIns.java index ab421c471..74cb75334 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/instructions/other/GetPropertyIns.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/instructions/other/GetPropertyIns.java @@ -24,6 +24,7 @@ import com.jpexs.decompiler.flash.abc.avm2.LocalDataArea; import com.jpexs.decompiler.flash.abc.avm2.exceptions.AVM2ExecutionException; import com.jpexs.decompiler.flash.abc.avm2.instructions.AVM2Instruction; import com.jpexs.decompiler.flash.abc.avm2.instructions.InstructionDefinition; +import com.jpexs.decompiler.flash.abc.avm2.model.ApplyTypeAVM2Item; import com.jpexs.decompiler.flash.abc.avm2.model.FindPropertyAVM2Item; import com.jpexs.decompiler.flash.abc.avm2.model.FullMultinameAVM2Item; import com.jpexs.decompiler.flash.abc.avm2.model.GetLexAVM2Item; @@ -166,7 +167,7 @@ public class GetPropertyIns extends InstructionDefinition { if (call) { thisPropType = localData.abcIndex.findPropertyCallType(localData.abc, new TypeItem(currentClassName), multinameStr, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, true, true); } else { - thisPropType = localData.abcIndex.findPropertyType(localData.abc, new TypeItem(currentClassName), multinameStr, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, true, true); + thisPropType = localData.abcIndex.findPropertyType(localData.abc, new TypeItem(currentClassName), multinameStr, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, true, true); } } if (!thisPropType.equals(TypeItem.UNBOUNDED)) { @@ -197,13 +198,42 @@ public class GetPropertyIns extends InstructionDefinition { if (obj instanceof GetPropertyAVM2Item) { if (((GetPropertyAVM2Item) obj).isStatic) { parentStatic = true; - } + } } - - if (call) { - type = localData.abcIndex.findPropertyCallType(localData.abc, receiverType, multiname.resolvedMultinameName, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, parentStatic, !parentStatic); - } else { - type = localData.abcIndex.findPropertyType(localData.abc, receiverType, multiname.resolvedMultinameName, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, parentStatic, !parentStatic); + if (receiverType instanceof ApplyTypeAVM2Item) { + ApplyTypeAVM2Item ati = (ApplyTypeAVM2Item) receiverType; + if (localData.abc.constants.getMultiname(multiname.multinameIndex).needsName()) { + if (call) { + type = TypeItem.UNBOUNDED; /*?*/ + } else { + type = ati.params.get(0); + } + } else { + receiverType = ati.object; + + if (receiverType.equals(new TypeItem("__AS3__.vec.Vector"))) { + String paramStr = ati.params.get(0).toString(); + switch(paramStr) { + case "double": + case "int": + case "uint": + receiverType = new TypeItem("__AS3__.vec.Vector$" + paramStr); + break; + default: + receiverType = new TypeItem("__AS3__.vec.Vector$object"); + } + } + + //TODO: handle method calls to return proper param type results + } + } + if (type == null) + { + if (call) { + type = localData.abcIndex.findPropertyCallType(localData.abc, receiverType, multiname.resolvedMultinameName, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, parentStatic, !parentStatic); + } else { + type = localData.abcIndex.findPropertyType(localData.abc, receiverType, multiname.resolvedMultinameName, localData.abc.constants.getMultiname(multiname.multinameIndex).namespace_index, parentStatic, !parentStatic); + } } } } diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/AVM2Item.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/AVM2Item.java index 24dd00e6e..4713cfd80 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/AVM2Item.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/AVM2Item.java @@ -115,7 +115,14 @@ public abstract class AVM2Item extends GraphTargetItem { HighlightData data = new HighlightData(); int multinameIndex = ((FullMultinameAVM2Item) propertyName).multinameIndex; int namespaceIndex = localData.constantsAvm2.getMultiname(multinameIndex).namespace_index; - data.propertyType = object.returnType().toString(); + GraphTargetItem returnType = object.returnType(); + if (returnType instanceof ApplyTypeAVM2Item) { + ApplyTypeAVM2Item ati = (ApplyTypeAVM2Item)returnType; + data.propertyType = ati.object.toString(); + data.propertySubType = ati.params.get(0).toString(); + } else { + data.propertyType = returnType.toString(); + } data.namespaceIndex = namespaceIndex; data.isStatic = isStatic; diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/ApplyTypeAVM2Item.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/ApplyTypeAVM2Item.java index 44d9d3ec3..232e69745 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/ApplyTypeAVM2Item.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/ApplyTypeAVM2Item.java @@ -123,4 +123,24 @@ public class ApplyTypeAVM2Item extends AVM2Item { ); } + @Override + public String toString() { + String ret = object.toString(); + if (!params.isEmpty()) { + ret += ".<"; + boolean first = true; + for (GraphTargetItem param : params) { + if (!first) { + ret += ", "; + } + ret += param.toString(); + first = false; + } + ret += ">"; + } + return ret; + } + + + } diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/CoerceAVM2Item.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/CoerceAVM2Item.java index 751135abe..70515998a 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/CoerceAVM2Item.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/model/CoerceAVM2Item.java @@ -105,6 +105,9 @@ public class CoerceAVM2Item extends AVM2Item { if (typeObj instanceof UnboundedTypeItem) { return typeObj; } + if (typeObj instanceof ApplyTypeAVM2Item) { + return typeObj; + } return new TypeItem(typeObj.toString()); } diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/parser/script/AbcIndexing.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/parser/script/AbcIndexing.java index 55c888982..f205ce27f 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/parser/script/AbcIndexing.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/abc/avm2/parser/script/AbcIndexing.java @@ -393,7 +393,7 @@ public final class AbcIndexing { public TraitIndex findProperty(PropertyDef prop, boolean findStatic, boolean findInstance) { /*System.out.println("searching " + prop); for (PropertyDef p : instanceProperties.keySet()) { - if (p.parent.equals(new TypeItem("String"))) { + if (p.parent.equals(new TypeItem("__AS3__.vec.Vector"))) { System.out.println("- " + p); } } diff --git a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/helpers/hilight/HighlightData.java b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/helpers/hilight/HighlightData.java index 66e2febd2..d5e839f37 100644 --- a/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/helpers/hilight/HighlightData.java +++ b/libsrc/ffdec_lib/src/com/jpexs/decompiler/flash/helpers/hilight/HighlightData.java @@ -50,6 +50,8 @@ public class HighlightData implements Cloneable, Serializable { public boolean isStatic = false; public String propertyType; + + public String propertySubType; public boolean isEmpty() { return !declaration && declaredType == null && localName == null @@ -57,7 +59,8 @@ public class HighlightData implements Cloneable, Serializable { && index == 0 && offset == 0 && regIndex == -1 && firstLineOffset == -1 && fileOffset == -1 && namespaceIndex == -1 - && propertyType == null; + && propertyType == null + && propertySubType == null; } public void merge(HighlightData data) { @@ -103,6 +106,9 @@ public class HighlightData implements Cloneable, Serializable { if (data.propertyType != null) { propertyType = data.propertyType; } + if (data.propertySubType != null) { + propertySubType = data.propertySubType; + } } @Override diff --git a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicAirDecompileTest.java b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicAirDecompileTest.java index 858000e01..b98625d86 100644 --- a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicAirDecompileTest.java +++ b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicAirDecompileTest.java @@ -240,7 +240,14 @@ public class ActionScript3ClassicAirDecompileTest extends ActionScript3Decompile + "1:\"B\",\r\n" + "2:\"C\"\r\n" + "};\r\n" - + "i = int(s.charAt(10));\r\n", + + "i = int(s.charAt(10));\r\n" + + "var v:Vector. = new Vector.();\r\n" + + "v.push(\"A\");\r\n" + + "v.push(\"B\");\r\n" + + "i = int(v[0]);\r\n" + + "s = v[1];\r\n" + + "s = v.join(\"x\");\r\n" + + "i = int(v.join(\"x\"));\r\n", false); } diff --git a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicDecompileTest.java b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicDecompileTest.java index f894b54e3..016ffc7c3 100644 --- a/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicDecompileTest.java +++ b/libsrc/ffdec_lib/test/com/jpexs/decompiler/flash/as3decompile/ActionScript3ClassicDecompileTest.java @@ -239,7 +239,14 @@ public class ActionScript3ClassicDecompileTest extends ActionScript3DecompileTes + "1:\"B\",\r\n" + "2:\"C\"\r\n" + "};\r\n" - + "i = int(s.charAt(10));\r\n", + + "i = int(s.charAt(10));\r\n" + + "var v:Vector. = new Vector.();\r\n" + + "v.push(\"A\");\r\n" + + "v.push(\"B\");\r\n" + + "i = int(v[0]);\r\n" + + "s = v[1];\r\n" + + "s = v.join(\"x\");\r\n" + + "i = int(v.join(\"x\"));\r\n", false); } diff --git a/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.air.swf b/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.air.swf index 5ec0f1219..d93a361ac 100644 Binary files a/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.air.swf and b/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.air.swf differ diff --git a/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.flex.swf b/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.flex.swf index 6192db34c..13fff6c80 100644 Binary files a/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.flex.swf and b/libsrc/ffdec_lib/testdata/as3_new/bin/as3_new.flex.swf differ diff --git a/libsrc/ffdec_lib/testdata/as3_new/src/tests/TestConvert.as b/libsrc/ffdec_lib/testdata/as3_new/src/tests/TestConvert.as index 56eaaa1df..8e6c093d7 100644 --- a/libsrc/ffdec_lib/testdata/as3_new/src/tests/TestConvert.as +++ b/libsrc/ffdec_lib/testdata/as3_new/src/tests/TestConvert.as @@ -36,6 +36,14 @@ package tests }; i = int(s.charAt(10)); + + var v:Vector. = new Vector.(); + v.push("A"); + v.push("B"); + i = int(v[0]); + s = v[1]; + s = v.join("x"); + i = int(v.join("x")); } } }