Procházet zdrojové kódy

Version 1.1.4.
Metadata generation for references from code are now generated out of line with the metadata generation for classes and methods. This avoids interleaving errors when code refers to features of classes that have not been allocated allocated indices. This is only an issue for the MethodDef, FieldDef and Param tables where the entries belonging to a particular parent must be contiguous in the table.
Fixing error in PEReader, where CSC and VB use inconsistent size data for exception tables. (VB does not count the size value in the total size, CSC does).

k_john_gough_cp před 15 roky
rodič
revize
7b8fdaa207

+ 10 - 15
PERWAPI/MDClassDefElems.cs

@@ -41,8 +41,6 @@ namespace QUT.PERWAPI
         private static readonly uint VisibilityMask = 0x07;
         private static readonly uint LayoutMask = 0x18;
         private static readonly uint StringFormatMask = 0x030000;
-        //private static readonly uint fieldListIx = 0, methListIx = 1, eventListIx = 2, propListIx = 3; 
-        //private static readonly uint	numListIx = 4;
 
         protected PEFile scope;
         uint flags;
@@ -56,9 +54,6 @@ namespace QUT.PERWAPI
         ArrayList properties = new ArrayList();
         ArrayList interfaces = new ArrayList();
         ArrayList methodImpls = new ArrayList();
-        //uint[] interfaceIndexes;
-        //private string[] eventNames, propertyNames, nestedNames;
-        //internal string[][] names = new string[numListIx][];
 
         /*-------------------- Constructors ---------------------------------*/
 
@@ -978,7 +973,17 @@ namespace QUT.PERWAPI
           }
 
           //uint startT = md.TableIndex(MDTable.TypeDef);
+          //uint startM = md.TableIndex(MDTable.Method);
+
           md.AddToTable(MDTable.TypeDef, this);
+          methodIx = md.TableIndex(MDTable.Method);
+          fieldIx = md.TableIndex(MDTable.Field);
+
+          //Console.WriteLine("Building tables for " + this.TypeName());
+          //Console.WriteLine("tIx {0}, methods {1} - {2}",
+          //  Hex.Short((short)startT),
+          //  Hex.Short((short)startM),
+          //  Hex.Short((short)md.TableIndex(MDTable.Method)));
 
           for (int i = 0; i < genericParams.Count; i++) {
             ((GenericParam)genericParams[i]).BuildMDTables(md);
@@ -993,22 +998,12 @@ namespace QUT.PERWAPI
 
           if (layout != null) layout.BuildMDTables(md);
 
-          //uint startM = md.TableIndex(MDTable.Method);
-
           // Console.WriteLine("adding methods " + methods.Count);
-          methodIx = md.TableIndex(MDTable.Method);
           for (int i = 0; i < methods.Count; i++) {
             ((MethodDef)methods[i]).BuildMDTables(md);
           }
 
-          //Console.WriteLine("Building tables for " + this.TypeName());
-          //Console.WriteLine("tIx {0}, methods {1} - {2}",
-          //  Hex.Short((short)startT),
-          //  Hex.Short((short)startM),
-          //  Hex.Short((short)md.TableIndex(MDTable.Method)));
-
           // Console.WriteLine("adding fields");
-          fieldIx = md.TableIndex(MDTable.Field);
           for (int i = 0; i < fields.Count; i++) {
             ((FieldDef)fields[i]).BuildMDTables(md);
           }

+ 1 - 0
PERWAPI/MDElements.cs

@@ -68,6 +68,7 @@ namespace QUT.PERWAPI
         /// </summary>
         protected ArrayList customAttributes;
         protected bool done = false;
+        
         protected bool sortTable = false;
         internal bool unresolved = false;
 

+ 37 - 18
PERWAPI/MDMethodElems.cs

@@ -1033,6 +1033,7 @@ namespace QUT.PERWAPI
         {
             md.AddToTable(MDTable.Method, this);
             nameIx = md.AddToStringsHeap(name);
+
             if (genericParams != null)
             {
                 for (int i = 0; i < genericParams.Count; i++)
@@ -1054,24 +1055,26 @@ namespace QUT.PERWAPI
                 localSig = new LocalSig(locals);
                 localSig.BuildMDTables(md);
             }
-            try
-            {
-                if (code != null)
-                {
-                    if (code.IsEmpty())
-                    {
-                        code = null;
-                    }
-                    else
-                    {
-                        code.BuildTables(md);
-                    }
-                }
-            }
-            catch (InstructionException ex)
-            {
-                throw new Exception(ex.AddMethodName(name));
-            }
+
+          // The following code is done out of line in method
+          // TraverseCode *after* all the method indices have
+          // been allocated in the metadata.
+          // (kjg, March 2010)
+            //try {
+            //  if (code != null) {
+            //    if (code.IsEmpty()) {
+            //      code = null;
+            //    }
+            //    else {
+            //      code.BuildTables(md);
+            //    }
+            //  }
+            //}
+            //catch (InstructionException ex) {
+            //  throw new Exception(ex.AddMethodName(name));
+            //}
+
+
             parIx = md.TableIndex(MDTable.Param);
             for (int i = 0; i < sig.numPars; i++)
             {
@@ -1081,6 +1084,22 @@ namespace QUT.PERWAPI
             sig.BuildTables(md);
         }
 
+        internal void TraverseCode(MetaDataOut md) {
+          try {
+            if (code != null) {
+              if (code.IsEmpty()) {
+                code = null;
+              }
+              else {
+                code.BuildTables(md);
+              }
+            }
+          }
+          catch (InstructionException ex) {
+            throw new Exception(ex.AddMethodName(name));
+          }
+        }
+
         internal sealed override void BuildCILInfo(CILWriter output)
         {
             if (genericParams != null)

+ 11 - 1
PERWAPI/MetaDataOut.cs

@@ -50,6 +50,16 @@ namespace QUT.PERWAPI
         {
         }
 
+      // Out of line generation of metadata for MethodDef code.
+      // This avoids the ordering errors for method and param indices
+      // when the code of a method refers to methods/fields of classes
+      // that have not been entered in the table.
+      // (kjg March 2010)
+        internal void BuildCode() {
+          foreach (object method in tables[(int)MDTable.Method])
+            (method as MethodDef).TraverseCode(this);
+        }
+
         Hashtable debugsigs = new Hashtable();
 
         /// <summary>
@@ -190,8 +200,8 @@ namespace QUT.PERWAPI
         }
 
         internal void AddToTable(MDTable tableIx, MetaDataElement elem) {
-          // updates Row field of the element
           // Console.WriteLine("Adding element to table " + (uint)tableIx);
+
           ArrayList table = GetTable(tableIx);
           if (table.Contains(elem)) {
             Console.Out.WriteLine("ERROR - element already in table " + tableIx);

+ 1 - 0
PERWAPI/PEFile.cs

@@ -364,6 +364,7 @@ namespace QUT.PERWAPI
         private void BuildMetaData()
         {
             BuildMDTables(metaData);
+            metaData.BuildCode();
             if (thisAssembly != null)
             {
                 thisAssembly.BuildMDTables(metaData);

+ 1 - 1
PERWAPI/PEReader.cs

@@ -1649,7 +1649,7 @@ namespace QUT.PERWAPI
                     if ((flags & CILInstructions.EHTable) == 0)
                         throw new Exception("Section not an Exception Handler Table");
                     int sectLen = ReadByte() + (ReadByte() << 8) + (ReadByte() << 16);
-                    int numClauses = sectLen - 4;
+                    int numClauses = sectLen; // -4;
                     if (fatSect)
                         numClauses /= 24;
                     else

+ 2 - 2
PERWAPI/Properties/AssemblyInfo.cs

@@ -29,5 +29,5 @@ using System.Runtime.InteropServices;
 //      Build Number
 //      Revision
 //
-[assembly: AssemblyVersion("1.1.3.41234")]
-[assembly: AssemblyFileVersion("1.1.3.41234")]
+[assembly: AssemblyVersion("1.1.4.44138")]
+[assembly: AssemblyFileVersion("1.1.4.44138")]

+ 2 - 2
SymbolRW/Properties/AssemblyInfo.cs

@@ -31,5 +31,5 @@ using System.Runtime.InteropServices;
 //
 // You can specify all the values or you can default the Revision and Build Numbers 
 // by using the '*' as shown below:
-[assembly: AssemblyVersion("1.1.3.41234")]
-[assembly: AssemblyFileVersion("1.1.2.41234")]
+[assembly: AssemblyVersion("1.1.4.44318")]
+[assembly: AssemblyFileVersion("1.1.2.44318")]