Ejemplo n.º 1
0
 private PdbToXmlConverter(XmlWriter writer, ISymUnmanagedReader symReader, MetadataReader metadataReader, PdbToXmlOptions options)
 {
     _symReader = symReader;
     _metadataReader = metadataReader;
     _writer = writer;
     _options = options;
 }
Ejemplo n.º 2
0
        public unsafe static void ToXml(TextWriter xmlWriter, Stream pdbStream, Stream peStream, PdbToXmlOptions options = PdbToXmlOptions.Default, string methodName = null)
        {
            IEnumerable<MethodHandle> methodHandles;
            var headers = new PEHeaders(peStream);
            byte[] metadata = new byte[headers.MetadataSize];
            peStream.Seek(headers.MetadataStartOffset, SeekOrigin.Begin);
            peStream.Read(metadata, 0, headers.MetadataSize);

            fixed (byte* metadataPtr = metadata)
            {
                var metadataReader = new MetadataReader((IntPtr)metadataPtr, metadata.Length);

                if (string.IsNullOrEmpty(methodName))
                {
                    methodHandles = metadataReader.MethodDefinitions;
                }
                else
                {
                    methodHandles = metadataReader.MethodDefinitions.
                        Where(methodHandle => GetQualifiedMethodName(metadataReader, methodHandle) == methodName);
                }

                ToXml(xmlWriter, pdbStream, metadataReader, options, methodHandles);
            }
        }
Ejemplo n.º 3
0
 private PdbToXmlConverter(XmlWriter writer, TempPdbReader pdbReader, MetadataReader metadataReader, PdbToXmlOptions options)
 {
     this.pdbReader = pdbReader;
     this.metadataReader = metadataReader;
     this.writer = writer;
     this.options = options;
 }
Ejemplo n.º 4
0
 internal static void VerifyPdb(
     this Compilation compilation,
     string expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber]int expectedValueSourceLine = 0,
     [CallerFilePath]string expectedValueSourcePath = null)
 {
     VerifyPdb(compilation, "", expectedPdb, format, options, expectedValueSourceLine, expectedValueSourcePath);
 }
Ejemplo n.º 5
0
 public CompilationVerifier VerifyPdb(
     string expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     _compilation.VerifyPdb(expectedPdb, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return(this);
 }
Ejemplo n.º 6
0
 internal static void VerifyPdb(
     this Compilation compilation,
     string expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdb(compilation, "", expectedPdb, format, options, expectedValueSourceLine, expectedValueSourcePath);
 }
        public static void VerifyPortablePdb(
            TestResource portable,
            string expectedXml,
            PdbToXmlOptions options = Options)
        {
            var portablePEStream  = new MemoryStream(portable.PE);
            var portablePdbStream = new MemoryStream(portable.Pdb);
            var actualXml         = PdbToXmlConverter.ToXml(portablePdbStream, portablePEStream, options);

            AssertEx.AssertLinesEqual(expectedXml, actualXml, "Comparing Portable PDB with expected XML");
        }
Ejemplo n.º 8
0
 public CompilationVerifier VerifyPdb(
     XElement expectedPdb,
     IMethodSymbol debugEntryPoint = null,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     _compilation.VerifyPdb(expectedPdb, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return(this);
 }
Ejemplo n.º 9
0
 internal static void VerifyPdb(
     this Compilation compilation,
     XElement expectedPdb,
     IMethodSymbol debugEntryPoint = null,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdb(compilation, "", expectedPdb, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
 }
Ejemplo n.º 10
0
 public static void VerifyPdb(
     this Compilation compilation,
     string expectedPdb,
     IEnumerable <EmbeddedText> embeddedTexts = null,
     IMethodSymbol debugEntryPoint            = null,
     DebugInformationFormat format            = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdb(compilation, "", expectedPdb, embeddedTexts, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
 }
Ejemplo n.º 11
0
 public static CompilationVerifier VerifyPdb(
     this CompilationVerifier verifier,
     XElement expectedPdb,
     IEnumerable <EmbeddedText> embeddedTexts = null,
     IMethodSymbol debugEntryPoint            = null,
     DebugInformationFormat format            = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     verifier.Compilation.VerifyPdb(expectedPdb, embeddedTexts, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return(verifier);
 }
Ejemplo n.º 12
0
 public static void GenXmlFromPdb(string exePath, string pdbPath, string outPath, PdbToXmlOptions options)
 {
     using (var exebits = new FileStream(exePath, FileMode.Open, FileAccess.Read))
     {
         using (var pdbbits = new FileStream(pdbPath, FileMode.Open, FileAccess.Read))
         {
             using (var sw = new StreamWriter(outPath, append: false, encoding: Encoding.UTF8))
             {
                 PdbToXmlConverter.ToXml(sw, pdbbits, exebits, options);
             }
         }
     }
 }
Ejemplo n.º 13
0
 public static CompilationVerifier VerifyPdb(
     this CompilationVerifier verifier,
     string qualifiedMethodName,
     XElement expectedPdb,
     IMethodSymbol debugEntryPoint = null,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     verifier.Compilation.VerifyPdb(qualifiedMethodName, expectedPdb, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return(verifier);
 }
Ejemplo n.º 14
0
 public static void GenXmlFromPdb(string exePath, string pdbPath, string outPath, PdbToXmlOptions options)
 {
     using (var exebits = new FileStream(exePath, FileMode.Open, FileAccess.Read))
     {
         using (var pdbbits = new FileStream(pdbPath, FileMode.Open, FileAccess.Read))
         {
             using (var sw = new StreamWriter(outPath, append: false, encoding: Encoding.UTF8))
             {
                 PdbToXmlConverter.ToXml(sw, pdbbits, exebits, options);
             }
         }
     }
 }
Ejemplo n.º 15
0
        public unsafe static void ToXml(TextWriter xmlWriter, Stream pdbStream, Stream peStream, PdbToXmlOptions options = PdbToXmlOptions.Default, string methodName = null)
        {
            IEnumerable<MethodHandle> methodHandles;
            var headers = new PEHeaders(peStream);
            byte[] metadata = new byte[headers.MetadataSize];
            peStream.Seek(headers.MetadataStartOffset, SeekOrigin.Begin);
            peStream.Read(metadata, 0, headers.MetadataSize);

            fixed (byte* metadataPtr = metadata)
            {
                var metadataReader = new MetadataReader((IntPtr)metadataPtr, metadata.Length);

                if (string.IsNullOrEmpty(methodName))
                {
                    methodHandles = metadataReader.MethodDefinitions;
                }
                else
                {
                    var matching = metadataReader.MethodDefinitions.
                        Where(methodHandle => GetQualifiedMethodName(metadataReader, methodHandle) == methodName).ToArray();

                    if (matching.Length == 0)
                    {
                        xmlWriter.WriteLine("<error>");
                        xmlWriter.WriteLine(string.Format("<message>No method '{0}' found in metadata.</message>", methodName));
                        xmlWriter.WriteLine("<available-methods>");

                        foreach (var methodHandle in metadataReader.MethodDefinitions)
                        {
                            xmlWriter.Write("<method><![CDATA[");
                            xmlWriter.Write(GetQualifiedMethodName(metadataReader, methodHandle));
                            xmlWriter.Write("]]></method>");
                            xmlWriter.WriteLine();
                        }

                        xmlWriter.WriteLine("</available-methods>");
                        xmlWriter.WriteLine("</error>");

                        return;
                    }

                    methodHandles = matching;
                }

                ToXml(xmlWriter, pdbStream, metadataReader, options, methodHandles);
            }
        }
Ejemplo n.º 16
0
        private static void VerifyPdbImpl(
            this Compilation compilation,
            IMethodSymbol debugEntryPoint,
            string qualifiedMethodName,
            XElement expectedPdb,
            DebugInformationFormat format,
            PdbToXmlOptions options,
            int expectedValueSourceLine,
            string expectedValueSourcePath,
            bool expectedIsXmlLiteral)
        {
            Assert.NotEqual(DebugInformationFormat.Embedded, format);

            if (format == 0 || format == DebugInformationFormat.Pdb)
            {
                XElement actualNativePdb = XElement.Parse(GetPdbXml(compilation, debugEntryPoint, options, qualifiedMethodName, portable: false));
                AssertXml.Equal(expectedPdb, actualNativePdb, expectedValueSourcePath, expectedValueSourceLine, expectedIsXmlLiteral);
            }

            if (format == 0 || format == DebugInformationFormat.PortablePdb)
            {
                XElement actualPortablePdb = XElement.Parse(GetPdbXml(compilation, debugEntryPoint, options, qualifiedMethodName, portable: true));

                // SymWriter doesn't create empty scopes. When the C# compiler uses forwarding CDI instead of a NamespaceScope
                // the scope is actually not empty - it logically contains the imports. Portable PDB does not used forwarding and thus
                // creates the scope. When generating PDB XML for testing the Portable DiaSymReader returns empty namespaces.
                RemoveEmptyScopes(actualPortablePdb);

                // sharing the same expected output with native PDB
                if (format == 0)
                {
                    RemoveNonPortablePdb(expectedPdb);

                    // TODO: remove
                    RemoveEmptySequencePoints(expectedPdb);

                    // remove scopes that only contained non-portable elements (namespace scopes)
                    RemoveEmptyScopes(expectedPdb);
                    RemoveMethodsWithNoSequencePoints(expectedPdb);
                    RemoveEmptyMethods(expectedPdb);
                }

                AssertXml.Equal(expectedPdb, actualPortablePdb, expectedValueSourcePath, expectedValueSourceLine, expectedIsXmlLiteral);
            }
        }
Ejemplo n.º 17
0
        private void TestGeneratePdb([CallerMemberName] string testName = null)
        {
            const PdbToXmlOptions options = PdbToXmlOptions.IncludeEmbeddedSources | PdbToXmlOptions.ThrowOnError | PdbToXmlOptions.IncludeTokens | PdbToXmlOptions.ResolveTokens | PdbToXmlOptions.IncludeMethodSpans;

            string    xmlFile    = Path.Combine(TestCasePath, testName + ".xml");
            string    xmlContent = File.ReadAllText(xmlFile);
            XDocument document   = XDocument.Parse(xmlContent);
            var       files      = document.Descendants("file").ToDictionary(f => f.Attribute("name").Value, f => f.Value);

            Tester.CompileCSharpWithPdb(Path.Combine(TestCasePath, testName + ".expected"), files);

            string peFileName       = Path.Combine(TestCasePath, testName + ".expected.dll");
            string pdbFileName      = Path.Combine(TestCasePath, testName + ".expected.pdb");
            var    moduleDefinition = new PEFile(peFileName);
            var    resolver         = new UniversalAssemblyResolver(peFileName, false, moduleDefinition.Reader.DetectTargetFrameworkId(), PEStreamOptions.PrefetchEntireImage);
            var    decompiler       = new CSharpDecompiler(moduleDefinition, resolver, new DecompilerSettings());

            using (FileStream pdbStream = File.Open(Path.Combine(TestCasePath, testName + ".pdb"), FileMode.OpenOrCreate, FileAccess.ReadWrite))
            {
                pdbStream.SetLength(0);
                PortablePdbWriter.WritePdb(moduleDefinition, decompiler, new DecompilerSettings(), pdbStream, noLogo: true);
                pdbStream.Position = 0;
                using (Stream peStream = File.OpenRead(peFileName))
                    using (Stream expectedPdbStream = File.OpenRead(pdbFileName))
                    {
                        using (StreamWriter writer = new StreamWriter(Path.ChangeExtension(pdbFileName, ".xml"), false, Encoding.UTF8))
                        {
                            PdbToXmlConverter.ToXml(writer, expectedPdbStream, peStream, options);
                        }
                        peStream.Position = 0;
                        using (StreamWriter writer = new StreamWriter(Path.ChangeExtension(xmlFile, ".generated.xml"), false, Encoding.UTF8))
                        {
                            PdbToXmlConverter.ToXml(writer, pdbStream, peStream, options);
                        }
                    }
            }
            string expectedFileName = Path.ChangeExtension(xmlFile, ".expected.xml");

            ProcessXmlFile(expectedFileName);
            string generatedFileName = Path.ChangeExtension(xmlFile, ".generated.xml");

            ProcessXmlFile(generatedFileName);
            Assert.AreEqual(Normalize(expectedFileName), Normalize(generatedFileName));
        }
Ejemplo n.º 18
0
 internal static void VerifyPdb(
     this Compilation compilation,
     string qualifiedMethodName,
     XElement expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdbImpl(
         compilation,
         qualifiedMethodName,
         expectedPdb,
         format,
         options,
         expectedValueSourceLine,
         expectedValueSourcePath,
         expectedIsXmlLiteral: true);
 }
Ejemplo n.º 19
0
        private static void VerifyPdbMatchesExpectedXml(
            Stream peStream,
            Stream pdbStream,
            string qualifiedMethodName,
            PdbToXmlOptions pdbToXmlOptions,
            string expectedPdb,
            int expectedValueSourceLine,
            string expectedValueSourcePath,
            bool expectedIsXmlLiteral,
            bool isPortable
            )
        {
            peStream.Position  = 0;
            pdbStream.Position = 0;
            var actualPdb = XElement
                            .Parse(
                PdbToXmlConverter.ToXml(
                    pdbStream,
                    peStream,
                    pdbToXmlOptions,
                    methodName: qualifiedMethodName
                    )
                )
                            .ToString();

            var(actual, expected) = AdjustToPdbFormat(
                actualPdb,
                expectedPdb,
                actualIsPortable: isPortable,
                actualIsConverted: false
                );

            AssertEx.AssertLinesEqual(
                expected,
                actual,
                $"PDB format: {(isPortable ? "Portable" : "Windows")}{Environment.NewLine}",
                expectedValueSourcePath,
                expectedValueSourceLine,
                escapeQuotes: !expectedIsXmlLiteral
                );
        }
Ejemplo n.º 20
0
 public static void VerifyPdb(
     this Compilation compilation,
     string qualifiedMethodName,
     string expectedPdb,
     IMethodSymbol debugEntryPoint = null,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options       = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdbImpl(
         compilation,
         debugEntryPoint,
         qualifiedMethodName,
         string.IsNullOrWhiteSpace(expectedPdb) ? "<symbols></symbols>" : expectedPdb,
         format,
         options,
         expectedValueSourceLine,
         expectedValueSourcePath,
         expectedIsXmlLiteral: false);
 }
Ejemplo n.º 21
0
        internal static void VerifyPdb(
            this Compilation compilation,
            string qualifiedMethodName,
            string expectedPdb,
            DebugInformationFormat format = 0,
            PdbToXmlOptions options       = 0,
            [CallerLineNumber] int expectedValueSourceLine  = 0,
            [CallerFilePath] string expectedValueSourcePath = null)
        {
            var expectedPdbXml = XElement.Parse(string.IsNullOrWhiteSpace(expectedPdb) ? "<symbols></symbols>" : expectedPdb);

            VerifyPdbImpl(
                compilation,
                qualifiedMethodName,
                expectedPdbXml,
                format,
                options,
                expectedValueSourceLine,
                expectedValueSourcePath,
                expectedIsXmlLiteral: false);
        }
Ejemplo n.º 22
0
        private static void VerifyConvertedPdbMatchesExpectedXml(
            Stream peStreamOriginal,
            Stream pdbStreamOriginal,
            string qualifiedMethodName,
            string expectedPdb,
            PdbToXmlOptions pdbToXmlOptions,
            bool expectedIsXmlLiteral,
            bool originalIsPortable)
        {
            var pdbStreamConverted = new MemoryStream();
            var converter          = new PdbConverter(diagnostic => Assert.True(false, diagnostic.ToString()));

            peStreamOriginal.Position  = 0;
            pdbStreamOriginal.Position = 0;

            if (originalIsPortable)
            {
                converter.ConvertPortableToWindows(peStreamOriginal, pdbStreamOriginal, pdbStreamConverted);
            }
            else
            {
                converter.ConvertWindowsToPortable(peStreamOriginal, pdbStreamOriginal, pdbStreamConverted);
            }

            pdbStreamConverted.Position = 0;
            peStreamOriginal.Position   = 0;

            var actualConverted  = AdjustForConversionArtifacts(XElement.Parse(PdbToXmlConverter.ToXml(pdbStreamConverted, peStreamOriginal, pdbToXmlOptions, methodName: qualifiedMethodName)).ToString());
            var adjustedExpected = AdjustForConversionArtifacts(expectedPdb);

            var(actual, expected) = AdjustToPdbFormat(actualConverted, adjustedExpected, actualIsPortable: !originalIsPortable, actualIsConverted: true);

            AssertEx.AssertLinesEqual(
                expected,
                actual,
                $"PDB format: {(originalIsPortable ? "Windows" : "Portable")} converted from {(originalIsPortable ? "Portable" : "Windows")}{Environment.NewLine}",
                expectedValueSourcePath: null,
                expectedValueSourceLine: 0,
                escapeQuotes: !expectedIsXmlLiteral);
        }
Ejemplo n.º 23
0
 public static void VerifyPdb(
     this Compilation compilation,
     string qualifiedMethodName,
     XElement expectedPdb,
     IEnumerable <EmbeddedText> embeddedTexts = null,
     IMethodSymbol debugEntryPoint            = null,
     DebugInformationFormat format            = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber] int expectedValueSourceLine  = 0,
     [CallerFilePath] string expectedValueSourcePath = null)
 {
     VerifyPdbImpl(
         compilation,
         embeddedTexts,
         debugEntryPoint,
         qualifiedMethodName,
         expectedPdb.ToString(),
         format,
         options,
         expectedValueSourceLine,
         expectedValueSourcePath,
         expectedIsXmlLiteral: true);
 }
Ejemplo n.º 24
0
        /// <summary>
        /// Load the PDB given the parameters at the ctor and spew it out to the XmlWriter specified
        /// at the ctor.
        /// </summary>
        private static void ToXml(TextWriter xmlWriter, Stream pdbStream, MetadataReader metadataReaderOpt, PdbToXmlOptions options, IEnumerable<MethodDefinitionHandle> methodHandles)
        {
            Debug.Assert(pdbStream != null);
            Debug.Assert((options & PdbToXmlOptions.ResolveTokens) == 0 || metadataReaderOpt != null);

            using (var writer = XmlWriter.Create(xmlWriter, s_xmlWriterSettings))
            {
                // metadata reader is on stack -> no owner needed
                var symReader = SymReaderFactory.CreateReader(pdbStream, metadataReaderOpt, metadataMemoryOwnerOpt: null);

                try
                {
                    var converter = new PdbToXmlConverter(writer, symReader, metadataReaderOpt, options);
                    converter.WriteRoot(methodHandles ?? metadataReaderOpt.MethodDefinitions);
                }
                finally
                {
                    ((ISymUnmanagedDispose)symReader).Destroy();
                }
            }
        }
Ejemplo n.º 25
0
 internal static void VerifyPdb(
     this Compilation compilation,
     string qualifiedMethodName,
     XElement expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber]int expectedValueSourceLine = 0,
     [CallerFilePath]string expectedValueSourcePath = null)
 {
     VerifyPdbImpl(
         compilation,
         qualifiedMethodName,
         expectedPdb,
         format,
         options,
         expectedValueSourceLine,
         expectedValueSourcePath,
         expectedIsXmlLiteral: true);
 }
Ejemplo n.º 26
0
        internal static void VerifyPdb(
            this Compilation compilation,
            string qualifiedMethodName,
            string expectedPdb,
            DebugInformationFormat format = 0,
            PdbToXmlOptions options = 0,
            [CallerLineNumber]int expectedValueSourceLine = 0,
            [CallerFilePath]string expectedValueSourcePath = null)
        {
            var expectedPdbXml = XElement.Parse(string.IsNullOrWhiteSpace(expectedPdb) ? "<symbols></symbols>" : expectedPdb);

            VerifyPdbImpl(
                compilation,
                qualifiedMethodName,
                expectedPdbXml,
                format,
                options,
                expectedValueSourceLine,
                expectedValueSourcePath,
                expectedIsXmlLiteral: false);
        }
Ejemplo n.º 27
0
 public static void GenXmlFromPdb(string exePath, string pdbPath, string outPath, PdbToXmlOptions options)
 {
     using (var peStream = new FileStream(exePath, FileMode.Open, FileAccess.Read))
         using (var pdbStream = new FileStream(pdbPath, FileMode.Open, FileAccess.Read))
             using (var dstFileStream = new FileStream(outPath, FileMode.Create, FileAccess.ReadWrite))
                 using (var sw = new StreamWriter(dstFileStream, Encoding.UTF8))
                 {
                     PdbToXmlConverter.ToXml(sw, pdbStream, peStream, options);
                 }
 }
Ejemplo n.º 28
0
        /// <summary>
        /// Load the PDB given the parameters at the ctor and spew it out to the XmlWriter specified
        /// at the ctor.
        /// </summary>
        private static void ToXml(TextWriter xmlWriter, Stream pdbStream, MetadataReader metadataReaderOpt, PdbToXmlOptions options, IEnumerable<MethodHandle> methodHandles)
        {
            Debug.Assert(pdbStream != null);
            Debug.Assert((options & PdbToXmlOptions.ResolveTokens) == 0 || metadataReaderOpt != null);

            XmlDocument doc = new XmlDocument();
            XmlWriter writer = doc.CreateNavigator().AppendChild();

            using (TempPdbReader pdbReader = TempPdbReader.Create(pdbStream))
            {
                if (pdbReader == null)
                {
                    Console.WriteLine("Error: No Symbol Reader could be initialized.");
                }

                var converter = new PdbToXmlConverter(writer, pdbReader, metadataReaderOpt, options);

                converter.WriteRoot(methodHandles ?? metadataReaderOpt.MethodDefinitions);
            }
                        
            writer.Close();

            // Save xml to disk
            doc.Save(xmlWriter);
        }
Ejemplo n.º 29
0
        /// <summary>
        /// Load the PDB given the parameters at the ctor and spew it out to the XmlWriter specified
        /// at the ctor.
        /// </summary>
        private static void ToXml(TextWriter xmlWriter, Stream pdbStream, MetadataReader metadataReaderOpt, PdbToXmlOptions options, IEnumerable <MethodDefinitionHandle> methodHandles)
        {
            Debug.Assert(pdbStream != null);
            Debug.Assert((options & PdbToXmlOptions.ResolveTokens) == 0 || metadataReaderOpt != null);

            XmlDocument doc    = new XmlDocument();
            XmlWriter   writer = doc.CreateNavigator().AppendChild();

            using (TempPdbReader pdbReader = TempPdbReader.Create(pdbStream))
            {
                if (pdbReader == null)
                {
                    Console.WriteLine("Error: No Symbol Reader could be initialized.");
                    return;
                }

                var converter = new PdbToXmlConverter(writer, pdbReader, metadataReaderOpt, options);

                converter.WriteRoot(methodHandles ?? metadataReaderOpt.MethodDefinitions);
            }

            writer.Close();

            // Save xml to disk
            doc.Save(xmlWriter);
        }
Ejemplo n.º 30
0
 public static void GenXmlFromDeltaPdb(string pdbPath, string outPath, PdbToXmlOptions options)
 {
     using (var deltaPdb = new FileStream(pdbPath, FileMode.Open, FileAccess.Read))
     {
         // There is no easy way to enumerate all method tokens that are present in the PDB.
         // So dump the first 255 method tokens (the ones that are not present will be skipped):
         File.WriteAllText(outPath, PdbToXmlConverter.DeltaPdbToXml(deltaPdb, Enumerable.Range(0x06000001, 255)));
     }
 }
Ejemplo n.º 31
0
        public unsafe static void ToXml(TextWriter xmlWriter, Stream pdbStream, Stream peStream, PdbToXmlOptions options = PdbToXmlOptions.Default, string methodName = null)
        {
            IEnumerable <MethodDefinitionHandle> methodHandles;
            var headers = new PEHeaders(peStream);

            byte[] metadata = new byte[headers.MetadataSize];
            peStream.Seek(headers.MetadataStartOffset, SeekOrigin.Begin);
            peStream.Read(metadata, 0, headers.MetadataSize);

            fixed(byte *metadataPtr = metadata)
            {
                var metadataReader = new MetadataReader(metadataPtr, metadata.Length);

                if (string.IsNullOrEmpty(methodName))
                {
                    methodHandles = metadataReader.MethodDefinitions;
                }
                else
                {
                    var matching = metadataReader.MethodDefinitions.
                                   Where(methodHandle => GetQualifiedMethodName(metadataReader, methodHandle) == methodName).ToArray();

                    if (matching.Length == 0)
                    {
                        xmlWriter.WriteLine("<error>");
                        xmlWriter.WriteLine(string.Format("<message>No method '{0}' found in metadata.</message>", methodName));
                        xmlWriter.WriteLine("<available-methods>");

                        foreach (var methodHandle in metadataReader.MethodDefinitions)
                        {
                            xmlWriter.Write("<method><![CDATA[");
                            xmlWriter.Write(GetQualifiedMethodName(metadataReader, methodHandle));
                            xmlWriter.Write("]]></method>");
                            xmlWriter.WriteLine();
                        }

                        xmlWriter.WriteLine("</available-methods>");
                        xmlWriter.WriteLine("</error>");

                        return;
                    }

                    methodHandles = matching;
                }

                ToXml(xmlWriter, pdbStream, metadataReader, options, methodHandles);
            }
        }
Ejemplo n.º 32
0
        internal static string GetPdbXml(
            Compilation compilation,
            PdbToXmlOptions options = 0,
            string qualifiedMethodName = "",
            bool portable = false)
        {
            string actual = null;
            using (var exebits = new MemoryStream())
            {
                using (var pdbbits = new MemoryStream())
                {
                    compilation.Emit(
                        exebits, 
                        pdbbits, 
                        options: EmitOptions.Default.WithDebugInformationFormat(portable ? DebugInformationFormat.PortablePdb : DebugInformationFormat.Pdb));

                    pdbbits.Position = 0;
                    exebits.Position = 0;

                    options |= PdbToXmlOptions.ResolveTokens | PdbToXmlOptions.ThrowOnError;
                    actual = PdbToXmlConverter.ToXml(pdbbits, exebits, options, methodName: qualifiedMethodName);
                }

                ValidateDebugDirectory(exebits, compilation.AssemblyName + ".pdb", portable);
            }

            return actual;
        }
Ejemplo n.º 33
0
        private static void VerifyPdbImpl(
            this Compilation compilation,
            string qualifiedMethodName,
            XElement expectedPdb,
            DebugInformationFormat format,
            PdbToXmlOptions options,
            int expectedValueSourceLine,
            string expectedValueSourcePath,
            bool expectedIsXmlLiteral)
        {
            Assert.NotEqual(DebugInformationFormat.Embedded, format);

            if (format == 0 || format == DebugInformationFormat.Pdb)
            {
                XElement actualNativePdb = XElement.Parse(GetPdbXml(compilation, options, qualifiedMethodName, portable: false));
                AssertXml.Equal(expectedPdb, actualNativePdb, expectedValueSourcePath, expectedValueSourceLine, expectedIsXmlLiteral);
            }

            if (format == 0 || format == DebugInformationFormat.PortablePdb)
            {
                XElement actualPortablePdb = XElement.Parse(GetPdbXml(compilation, options, qualifiedMethodName, portable: true));

                // SymWriter doesn't create empty scopes. When the C# compiler uses forwarding CDI instead of a NamespaceScope
                // the scope is actually not empty - it logically contains the imports. Portable PDB does not used forwarding and thus
                // creates the scope. When generating PDB XML for testing the Portable DiaSymReader returns empty namespaces.
                RemoveEmptyScopes(actualPortablePdb);

                // sharing the same expected output with native PDB
                if (format == 0)
                {
                    RemoveNonPortablePdb(expectedPdb);

                    // TODO: remove
                    RemoveEmptySequencePoints(expectedPdb);

                    // remove scopes that only contained non-portable elements (namespace scopes)
                    RemoveEmptyScopes(expectedPdb);

                    RemoveEmptyMethods(expectedPdb);
                }

                AssertXml.Equal(expectedPdb, actualPortablePdb, expectedValueSourcePath, expectedValueSourceLine, expectedIsXmlLiteral);
            }
        }
 public CompilationVerifier VerifyPdb(
     string expectedPdb,
     IMethodSymbol debugEntryPoint = null,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber]int expectedValueSourceLine = 0,
     [CallerFilePath]string expectedValueSourcePath = null)
 {
     _compilation.VerifyPdb(expectedPdb, debugEntryPoint, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return this;
 }
Ejemplo n.º 35
0
        public static void CompileCSharpWithPdb(string assemblyName, Dictionary <string, string> sourceFiles, PdbToXmlOptions options)
        {
            var parseOptions = new CSharpParseOptions(languageVersion: Microsoft.CodeAnalysis.CSharp.LanguageVersion.Latest);

            List <EmbeddedText> embeddedTexts = new List <EmbeddedText>();
            List <SyntaxTree>   syntaxTrees   = new List <SyntaxTree>();

            foreach (KeyValuePair <string, string> file in sourceFiles)
            {
                var sourceText = SourceText.From(file.Value, new UTF8Encoding(false), SourceHashAlgorithm.Sha256);
                syntaxTrees.Add(SyntaxFactory.ParseSyntaxTree(sourceText, parseOptions, file.Key));
                embeddedTexts.Add(EmbeddedText.FromSource(file.Key, sourceText));
            }

            var compilation = CSharpCompilation.Create(Path.GetFileNameWithoutExtension(assemblyName),
                                                       syntaxTrees, defaultReferences.Value,
                                                       new CSharpCompilationOptions(
                                                           OutputKind.DynamicallyLinkedLibrary,
                                                           platform: Platform.AnyCpu,
                                                           optimizationLevel: OptimizationLevel.Release,
                                                           allowUnsafe: true,
                                                           deterministic: true
                                                           ));

            using (FileStream peStream = File.Open(assemblyName + ".dll", FileMode.OpenOrCreate, FileAccess.ReadWrite))
                using (FileStream pdbStream = File.Open(assemblyName + ".pdb", FileMode.OpenOrCreate, FileAccess.ReadWrite)) {
                    var emitResult = compilation.Emit(peStream, pdbStream, options: new EmitOptions(debugInformationFormat: DebugInformationFormat.PortablePdb, pdbFilePath: assemblyName + ".pdb"), embeddedTexts: embeddedTexts);
                    if (!emitResult.Success)
                    {
                        StringBuilder b = new StringBuilder("Compiler error:");
                        foreach (var diag in emitResult.Diagnostics)
                        {
                            b.AppendLine(diag.ToString());
                        }
                        throw new Exception(b.ToString());
                    }
                }
        }
Ejemplo n.º 36
0
        /// <summary>
        /// Load the PDB given the parameters at the ctor and spew it out to the XmlWriter specified
        /// at the ctor.
        /// </summary>
        private static void ToXml(TextWriter xmlWriter, Stream pdbStream, MetadataReader metadataReaderOpt, PdbToXmlOptions options, IEnumerable<MethodDefinitionHandle> methodHandles)
        {
            Debug.Assert(pdbStream != null);
            Debug.Assert((options & PdbToXmlOptions.ResolveTokens) == 0 || metadataReaderOpt != null);

            XmlDocument doc = new XmlDocument();
            XmlWriter writer = doc.CreateNavigator().AppendChild();

            using (SymReader symReader = new SymReader(pdbStream, metadataReaderOpt))
            {
                var converter = new PdbToXmlConverter(writer, symReader, metadataReaderOpt, options);

                converter.WriteRoot(methodHandles ?? metadataReaderOpt.MethodDefinitions);
            }

            writer.Close();

            // Save xml to disk
            doc.Save(xmlWriter);
        }
Ejemplo n.º 37
0
 private PdbToXmlConverter(XmlWriter writer, TempPdbReader pdbReader, MetadataReader metadataReader, PdbToXmlOptions options)
 {
     this.pdbReader      = pdbReader;
     this.metadataReader = metadataReader;
     this.writer         = writer;
     this.options        = options;
 }
Ejemplo n.º 38
0
 public static string ToXml(Stream pdbStream, Stream peStream, PdbToXmlOptions options = PdbToXmlOptions.ResolveTokens, string methodName = null)
 {
     var writer = new StringWriter();
     ToXml(writer, pdbStream, peStream, options, methodName);
     return writer.ToString();
 }
 public CompilationVerifier VerifyPdb(
     string qualifiedMethodName,
     XElement expectedPdb,
     DebugInformationFormat format = 0,
     PdbToXmlOptions options = 0,
     [CallerLineNumber]int expectedValueSourceLine = 0,
     [CallerFilePath]string expectedValueSourcePath = null)
 {
     _compilation.VerifyPdb(qualifiedMethodName, expectedPdb, format, options, expectedValueSourceLine, expectedValueSourcePath);
     return this;
 }
Ejemplo n.º 40
0
 public static string ToXml(Stream pdbStream, byte[] peImage, PdbToXmlOptions options = PdbToXmlOptions.ResolveTokens, string methodName = null)
 {
     var writer = new StringWriter();
     ToXml(writer, pdbStream, new MemoryStream(peImage), options, methodName);
     return writer.ToString();
 }