You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@flex.apache.org by ah...@apache.org on 2013/10/11 08:19:23 UTC

[08/10] git commit: [flex-sdk] [refs/heads/develop] - add more details to abc output

add more details to abc output


Project: http://git-wip-us.apache.org/repos/asf/flex-sdk/repo
Commit: http://git-wip-us.apache.org/repos/asf/flex-sdk/commit/23d9fda8
Tree: http://git-wip-us.apache.org/repos/asf/flex-sdk/tree/23d9fda8
Diff: http://git-wip-us.apache.org/repos/asf/flex-sdk/diff/23d9fda8

Branch: refs/heads/develop
Commit: 23d9fda8b21fef66527c52fd5813de9057f06976
Parents: 1a4df28
Author: Alex Harui <ah...@apache.org>
Authored: Wed Oct 9 20:39:20 2013 -0700
Committer: Alex Harui <ah...@apache.org>
Committed: Thu Oct 10 23:18:38 2013 -0700

----------------------------------------------------------------------
 .../src/java/flash/swf/tools/AbcPrinter.java    | 141 +++++++++++++++++--
 1 file changed, 129 insertions(+), 12 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/flex-sdk/blob/23d9fda8/modules/swfutils/src/java/flash/swf/tools/AbcPrinter.java
----------------------------------------------------------------------
diff --git a/modules/swfutils/src/java/flash/swf/tools/AbcPrinter.java b/modules/swfutils/src/java/flash/swf/tools/AbcPrinter.java
index 8baafa0..4fe4198 100644
--- a/modules/swfutils/src/java/flash/swf/tools/AbcPrinter.java
+++ b/modules/swfutils/src/java/flash/swf/tools/AbcPrinter.java
@@ -29,11 +29,13 @@ import java.util.HashMap;
 public class AbcPrinter 
 {
     private byte[] abc;
+    private int abcEnd;
     private PrintWriter out;
     private boolean showOffset;
     private boolean showByteCode;
     private int indent;
     private int offset = 0;
+    private long numMetadata;
 		
     private int[] intConstants;
     private long[] uintConstants;
@@ -42,14 +44,18 @@ public class AbcPrinter
     private String[] namespaceConstants;
     private String[][] namespaceSetConstants;
     private MultiName[] multiNameConstants;
+    private String kAbcCorrupt = "Verify Error: ABC Corrupt";
+
 		
     private MethodInfo[] methods;
     private String[] instanceNames;
+    private String[] Names;
     private String indentString;
 		
     public AbcPrinter(byte[] abc, PrintWriter out, boolean showOffset, int indent, boolean showByteCode)
     {
         this.abc = abc;
+        this.abcEnd = abc.length;
         this.out = out;
         this.showOffset = showOffset;
         this.showByteCode = showByteCode;
@@ -583,6 +589,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Integer Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         intConstants = new int[(n > 0) ? (int)n : 1];
         intConstants[0] = 0;
         for (int i = 1; i < n; i++)
@@ -599,6 +607,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Unsigned Integer Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         uintConstants = new long[(n > 0) ? (int)n : 1];
         uintConstants[0] = 0;
         for (int i = 1; i < n; i++)
@@ -615,6 +625,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Floating Point Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         if (n > 0)
             offset += (n - 1) * 8;
     }
@@ -624,13 +636,21 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " String Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         stringConstants = new String[(n > 0) ? (int)n : 1];
         stringConstants[0] = "";
         for (int i = 1; i < n; i++)
         {
             printOffset();
-            String s = readUTFBytes(readU32());
+            long strlen = readU32();
+            if (((strlen & 0xc0000000) != 0) || abcEnd <= offset + strlen)
+            	out.println(kAbcCorrupt + "strlen");
+            String s = readUTFBytes(strlen);
             stringConstants[i] = s;
+            s = s.replace("\r\n", "\\r\\n");
+            s = s.replace("\n", "\\n");
+            s = s.replace("\r", "\\r");
             out.println(" " + s);
         }
     }
@@ -640,6 +660,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Namespace Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         namespaceConstants = new String[(n > 0) ? (int)n : 1];
         namespaceConstants[0] = "public";
         for (int i = 1; i < n; i++)
@@ -666,11 +688,15 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Namespace Set Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         namespaceSetConstants = new String[(n > 0) ? (int)n : 1][];
         namespaceSetConstants[0] = new String[0];
         for (int i = 1; i < n; i++)
         {
             long val = readU32();
+            if (val > abcEnd - offset)
+               	out.println(kAbcCorrupt);
             String[] nsset = new String[(int)val];
             namespaceSetConstants[i] = nsset;
             for (int j = 0; j < val; j++)
@@ -685,6 +711,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " MultiName Constant Pool Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);       
         multiNameConstants = new MultiName[(n > 0) ? (int)n : 1];
         multiNameConstants[0] = new MultiName();
         for (int i = 1; i < n; i++)
@@ -723,6 +751,8 @@ public class AbcPrinter
                 int nameIndex = (int)readU32();
                 MultiName mn = multiNameConstants[nameIndex];
                 int count = (int)readU32();
+                if (count != 1)
+                   	out.println(kAbcCorrupt + "more than one typename");
                 MultiName types[] = new MultiName[count];
                 for (int t = 0; t < count; t++)
                 {
@@ -734,6 +764,27 @@ public class AbcPrinter
             }
             out.println(multiNameConstants[i]);
         }
+        // verify vectors (yes, the AVM does this)
+        for (int i = 1; i < n; i++)
+        {
+        	MultiName mn = multiNameConstants[i];
+        	if (mn.kind != 0x1D)
+        		continue;
+        	MultiName typeName = mn.typeName;
+        	if (typeName.kind == 0x1D)
+        		out.println(kAbcCorrupt + "typename is also a typename");
+        	HashMap<MultiName, String> seenMap = new HashMap<MultiName, String>();
+    		MultiName type = mn.types[0];
+        	while (type != null)
+        	{
+        		if (type.kind != 0x1D)
+        			break;
+        		seenMap.put(type, type.toString());
+        		type = type.types[0];
+        		if (seenMap.containsKey(type))
+            		out.println(kAbcCorrupt + "type cycle");        			
+        	}
+        }
     }
 		
     void printMethods()
@@ -741,6 +792,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Method Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         methods = new MethodInfo[(int)n];
         for (int i = 0; i < n; i++)
         {
@@ -772,6 +825,8 @@ public class AbcPrinter
                     m.optionIndex[k] = (int)readU32();
                     m.optionKinds[k] = abc[offset++];
                 }
+                if (m.optionCount == 0 || m.optionCount > m.paramCount)
+                	out.println(kAbcCorrupt);
             }
             if ((m.flags & 0x80) == 0x80)
             {
@@ -807,6 +862,9 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Metadata Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
+        numMetadata = n;
         for (int i = 0; i < n; i++)
         {
             int start = offset;
@@ -837,6 +895,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Instance Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         instanceNames = new String[(int)n];
         for (int i = 0; i < n; i++)
         {
@@ -849,6 +909,8 @@ public class AbcPrinter
             if ((b & 0x8) == 0x8)
                 readU32();	// eat protected namespace
             long val = readU32();
+            if (val >= 0x10000000)
+            	out.println(kAbcCorrupt);
             String s = "";
             for (int j = 0; j < val; j++)
             {
@@ -866,7 +928,7 @@ public class AbcPrinter
                     out.print(hex(abc[(int)x]) + " ");
                 }
             }
-            out.print(name + " ");
+            out.print("Instance Traits for: " + name + " ");
             if (base.length() > 0)
                 out.print("extends " + base + " ");
             if (s.length() > 0)
@@ -876,6 +938,8 @@ public class AbcPrinter
             int numTraits = (int)readU32(); // number of traits
             printOffset();
             out.println(numTraits + " Traits Entries");
+            if (numTraits > abcEnd - offset)
+            	out.println(kAbcCorrupt);
             for (int j = 0; j < numTraits; j++)
             {
                 printOffset();
@@ -897,20 +961,30 @@ public class AbcPrinter
                     readU32();	// id
                     readU32();	// value;
                     break;
-                default:
+                case 0x01:
+                case 0x02:
+                case 0x03:
+                case 0x05:
                     readU32();	// id
                     mi = methods[(int)readU32()];  // method
                     mi.name = s;
                     mi.className = name;
                     mi.kind = kind;
+                    if (mi.sawTraits)
+                    	out.println(kAbcCorrupt + "sawTraits");
+                    mi.sawTraits = true;
                     break;
+                default:
+                	out.println(kAbcCorrupt + "Unknown Trait");
                 }
                 if ((b >> 4 & 0x4) == 0x4)
                 {
                     val = readU32();	// metadata count
                     for (int k = 0; k < val; k++)
                     {
-                        readU32();	// metadata
+                        long index = readU32();	// metadata
+                        if (index >= numMetadata)
+                        	out.println(kAbcCorrupt);
                     }
                 }
                 if (showByteCode)
@@ -942,7 +1016,7 @@ public class AbcPrinter
                     out.print(hex(abc[(int)x]) + " ");
                 }
             }
-            out.print(name + " ");
+            out.print("Class Traits for: " + name + " ");
             if (base.length() > 0)
                 out.print("extends " + base + " ");
             out.println("");
@@ -950,6 +1024,8 @@ public class AbcPrinter
             int numTraits = (int)readU32(); // number of traits
             printOffset();
             out.println(numTraits + " Traits Entries");
+            if (numTraits > abcEnd - offset)
+            	out.println(kAbcCorrupt);
             for (int j = 0; j < numTraits; j++)
             {
                 printOffset();
@@ -971,20 +1047,30 @@ public class AbcPrinter
                     readU32();	// id
                     readU32();	// value;
                     break;
-                default:
+                case 0x01:
+                case 0x02:
+                case 0x03:
+                case 0x05:
                     readU32();	// id
                     mi = methods[(int)readU32()];  // method
                     mi.name = s;
                     mi.className = name;
                     mi.kind = kind;
+                    if (mi.sawTraits)
+                    	out.println(kAbcCorrupt + "sawTraits");
+                    mi.sawTraits = true;
                     break;
+                 default:
+                 	out.println(kAbcCorrupt);
                 }
                 if ((b >> 4 & 0x4) == 0x4)
                 {
                     int val = (int)readU32();	// metadata count
                     for (int k = 0; k < val; k++)
                     {
-                        readU32();	// metadata
+                        long index = readU32();	// metadata
+                        if (index > numMetadata)
+                        	out.println(kAbcCorrupt);
                     }
                 }
                 if (showByteCode)
@@ -1004,6 +1090,8 @@ public class AbcPrinter
         long n = readU32();
         printOffset();
         out.println(n + " Script Entries");
+        if (n > abcEnd - offset)
+        	out.println(kAbcCorrupt);
         for (int i = 0; i < n; i++)
         {
             int start = offset;
@@ -1026,6 +1114,8 @@ public class AbcPrinter
             int numTraits = (int)readU32(); // number of traits
             printOffset();
             out.println(numTraits + " Traits Entries");
+            if (numTraits > abcEnd - offset)
+            	out.println(kAbcCorrupt);
             for (int j = 0; j < numTraits; j++)
             {
                 printOffset();
@@ -1037,6 +1127,10 @@ public class AbcPrinter
                 {
                 case 0x00:	// slot
                 case 0x06:	// const
+                	if (kind == 0x00)
+                		s = "slot trait:  " + s;
+                	else
+                		s = "const trait:  " + s;
                     readU32();	// id
                     readU32();	// type
                     int index = (int)readU32();	// index;
@@ -1044,23 +1138,34 @@ public class AbcPrinter
                         offset++;	// kind
                     break;
                 case 0x04:	// class
+                	s = "class trait:  " + s;
                     readU32();	// id
-                    readU32();	// value;
+                    s += " " + instanceNames[(int)readU32()];	// value;
                     break;
-                default:
+                case 0x01:
+                case 0x02:
+                case 0x03:
+                case 0x05:
                     readU32();	// id
                     mi = methods[(int)readU32()];  // method
                     mi.name = s;
                     mi.className = name;
                     mi.kind = kind;
+                    if (mi.sawTraits)
+                    	out.println(kAbcCorrupt + "sawTraits");
+                    mi.sawTraits = true;
                     break;
+                 default:
+                 	out.println(kAbcCorrupt + "Unknown trait");
                 }
                 if ((b >> 4 & 0x4) == 0x4)
                 {
                     int val = (int)readU32();	// metadata count
                     for (int k = 0; k < val; k++)
                     {
-                        readU32();	// metadata
+                        long index = readU32();	// metadata
+                        if (index > numMetadata)
+                        	out.println(kAbcCorrupt);
                     }
                 }
                 if (showByteCode)
@@ -1103,6 +1208,8 @@ public class AbcPrinter
                     out.print("   ");
                 }
             }
+            if (abcEnd < codeLength + offset)
+            	out.println(kAbcCorrupt);
             MethodInfo mi = methods[methodIndex];
             out.print(traitKinds[mi.kind] + " ");
             out.print(mi.className + "::" + mi.name + "(");
@@ -1308,6 +1415,8 @@ public class AbcPrinter
             int numTraits = (int)readU32(); // number of traits
             printOffset();
             out.println(numTraits + " Traits Entries");
+            if (numTraits > abcEnd - offset)
+            	out.println(kAbcCorrupt);
             for (int j = 0; j < numTraits; j++)
             {
                 printOffset();
@@ -1329,17 +1438,24 @@ public class AbcPrinter
                     readU32();	// id
                     readU32();	// value;
                     break;
-                default:
+                case 0x01:
+                case 0x02:
+                case 0x03:
+                case 0x05:
                     readU32();	// id
                     readU32();  // method
                     break;
+                default:
+                	out.println(kAbcCorrupt);
                 }
                 if ((b >> 4 & 0x4) == 0x4)
                 {
                     int val = (int)readU32();	// metadata count
                     for (int k = 0; k < val; k++)
                     {
-                        readU32();	// metadata
+                        long index = readU32();	// metadata
+                        if (index > numMetadata)
+                        	out.println(kAbcCorrupt);
                     }
                 }
                 if (showByteCode)
@@ -1447,6 +1563,7 @@ public class AbcPrinter
         int[] optionIndex;
         int[] paramNames;
         String className;
+        boolean sawTraits;
     }
 		
     class LabelMgr