Example #1
0
        private Object ResolveAssemblyReference(AssemblyReferenceHandle handle)
        {
            AssemblyReference assemblyReference = _metadataReader.GetAssemblyReference(handle);

            AssemblyName an = new AssemblyName();

            an.Name    = _metadataReader.GetString(assemblyReference.Name);
            an.Version = assemblyReference.Version;

            var publicKeyOrToken = _metadataReader.GetBlobBytes(assemblyReference.PublicKeyOrToken);

            if ((an.Flags & AssemblyNameFlags.PublicKey) != 0)
            {
                an.SetPublicKey(publicKeyOrToken);
            }
            else
            {
                an.SetPublicKeyToken(publicKeyOrToken);
            }

            an.CultureName = _metadataReader.GetString(assemblyReference.Culture);
            an.ContentType = GetContentTypeFromAssemblyFlags(assemblyReference.Flags);

            return(Context.ResolveAssembly(an));
        }
        private IReadOnlyList <SourceLinkMap> GetSourceLinkInformation()
        {
            var sl = (from cdi in _reader.CustomDebugInformation
                      let cd = _reader.GetCustomDebugInformation(cdi)
                               let kind = _reader.GetGuid(cd.Kind)
                                          where kind == SourceLinkGuid
                                          let bl = _reader.GetBlobBytes(cd.Value)
                                                   select Encoding.UTF8.GetString(bl))
                     .FirstOrDefault();

            if (sl != null)
            {
                try
                {
                    /* Some tools, like GitLink generate incorrectly escaped JSON:
                     *
                     * {
                     * "documents": {
                     *  "C:\projects\cefsharp\*": "https://raw.github.com/CefSharp/CefSharp/4f88ad11416e93dde4b52216800efd42ba3b9c8a/*"
                     * }
                     * }
                     *
                     * Catch the exception and try to fix the key
                     */
                    JObject?jobj = null;
                    try
                    {
                        jobj = JObject.Parse(sl);
                    }
                    catch (JsonReaderException e) when(e.Path == "documents")
                    {
                        sl   = sl.Replace(@"\", @"\\");
                        jobj = JObject.Parse(sl);
                    }

                    var docs = (JObject)jobj["documents"];

                    var slis = (from prop in docs.Properties()
                                select new SourceLinkMap
                    {
                        Base = prop.Name.Replace(@"\", @"/"),             // use forward slashes for the url,
                        Location = prop.Value.Value <string>()
                    })
                               .ToList();

                    return(slis);
                }
                catch (JsonReaderException jse)
                {
                    throw new InvalidDataException("SourceLink data could not be parsed", jse);
                }
            }

            return(Array.Empty <SourceLinkMap>());
        }
Example #3
0
        /// <summary>
        /// Unpacks all files stored in a PortablePDB meta-data. The key in the dictionary is the location of a source file
        /// on the build machine. The value is the content of the source file itself.
        /// The function will throw an exception if PortablePDB file is not found or anything else went wrong.
        /// </summary>
        /// <param name="pdbFilePath">Path to PortablePDB file to load source files from.</param>
        public static Dictionary <string, CompressedSourceFile> GetEmbeddedFiles(string pdbFilePath)
        {
            Dictionary <string, CompressedSourceFile> embeddedFiles = new Dictionary <string, CompressedSourceFile>();

            using (FileStream stream = File.OpenRead(pdbFilePath))
                using (MetadataReaderProvider metadataReaderProvider = MetadataReaderProvider.FromPortablePdbStream(stream))
                {
                    MetadataReader metadataReader = metadataReaderProvider.GetMetadataReader();
                    CustomDebugInformationHandleCollection customDebugInformationHandles = metadataReader.CustomDebugInformation;
                    foreach (var customDebugInformationHandle in customDebugInformationHandles)
                    {
                        CustomDebugInformation customDebugInformation = metadataReader.GetCustomDebugInformation(customDebugInformationHandle);
                        if (metadataReader.GetGuid(customDebugInformation.Kind) == EmbeddedSource)
                        {
                            byte[] embeddedSource             = metadataReader.GetBlobBytes(customDebugInformation.Value);
                            Int32  uncompressedSourceFileSize = BitConverter.ToInt32(embeddedSource, 0);
                            if (uncompressedSourceFileSize != 0)
                            {
                                Document document       = metadataReader.GetDocument((DocumentHandle)customDebugInformation.Parent);
                                string   sourceFileName = System.IO.Path.GetFullPath(metadataReader.GetString(document.Name));
                                embeddedFiles.Add(sourceFileName, new CompressedSourceFile(embeddedSource));
                            }
                        }
                    }
                }
            return(embeddedFiles);
        }
        public static AssemblyIdentity TryGetAssemblyIdentity(string filePath)
        {
            try
            {
                using (FileStream stream = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite | FileShare.Delete))
                    using (PEReader peReader = new PEReader(stream))
                    {
                        MetadataReader metadataReader = peReader.GetMetadataReader();

                        AssemblyDefinition assemblyDefinition = metadataReader.GetAssemblyDefinition();

                        string  name    = metadataReader.GetString(assemblyDefinition.Name);
                        Version version = assemblyDefinition.Version;

                        StringHandle  cultureHandle = assemblyDefinition.Culture;
                        string        cultureName   = (!cultureHandle.IsNil) ? metadataReader.GetString(cultureHandle) : null;
                        AssemblyFlags flags         = assemblyDefinition.Flags;

                        bool                  hasPublicKey     = (flags & AssemblyFlags.PublicKey) != 0;
                        BlobHandle            publicKeyHandle  = assemblyDefinition.PublicKey;
                        ImmutableArray <byte> publicKeyOrToken = !publicKeyHandle.IsNil
                        ? metadataReader.GetBlobBytes(publicKeyHandle).AsImmutableOrNull()
                        : default(ImmutableArray <byte>);
                        return(new AssemblyIdentity(name, version, cultureName, publicKeyOrToken, hasPublicKey));
                    }
            }
            catch { }

            return(null);
        }
Example #5
0
        private Object ResolveAssemblyReference(AssemblyReferenceHandle handle)
        {
            AssemblyReference assemblyReference = _metadataReader.GetAssemblyReference(handle);

            AssemblyName an = new AssemblyName();

            an.Name    = _metadataReader.GetString(assemblyReference.Name);
            an.Version = assemblyReference.Version;

            var publicKeyOrToken = _metadataReader.GetBlobBytes(assemblyReference.PublicKeyOrToken);

            if ((assemblyReference.Flags & AssemblyFlags.PublicKey) != 0)
            {
                an.SetPublicKey(publicKeyOrToken);
            }
            else
            {
                an.SetPublicKeyToken(publicKeyOrToken);
            }

            an.CultureName = _metadataReader.GetString(assemblyReference.Culture);
            an.ContentType = GetContentTypeFromAssemblyFlags(assemblyReference.Flags);

            var assembly = _moduleResolver.ResolveAssembly(an, throwIfNotFound: false);

            if (assembly == null)
            {
                return(ResolutionFailure.GetAssemblyResolutionFailure(an.Name));
            }
            else
            {
                return(assembly);
            }
        }
Example #6
0
        private static void WriteAssemblyToXml(MetadataReader metaReader, XmlTextWriter xmlWriter)
        {
            if (!metaReader.IsAssembly)
            {
                return;
            }

            var assembly = metaReader.GetAssemblyDefinition();

            xmlWriter.WriteStartElement("File");
            xmlWriter.WriteAttributeString("AssemblyName", metaReader.GetString(assembly.Name));
            xmlWriter.WriteAttributeString("Version", assembly.Version.ToString(4));

            var culture = metaReader.GetString(assembly.Culture);

            xmlWriter.WriteAttributeString("Culture", string.IsNullOrEmpty(culture) ? "neutral" : culture);


            var publicKey      = metaReader.GetBlobBytes(assembly.PublicKey);
            var publicKeyToken = PublicKeyTokenCalculator.CalculatePublicKeyToken(publicKey);

            var publicKeyTokenStr = BitConverter.ToString(publicKeyToken).Replace("-", string.Empty).ToLowerInvariant();

            xmlWriter.WriteAttributeString("PublicKeyToken", publicKeyTokenStr);

            xmlWriter.WriteAttributeString("InGac", "false");
            xmlWriter.WriteAttributeString("ProcessorArchitecture", "MSIL");

            xmlWriter.WriteEndElement();
        }
Example #7
0
        public unsafe int GetSigFromToken(
            int tkSignature,  // Signature token.
            out byte *ppvSig, // return pointer to signature blob
            out int pcbSig
            )                 // return size of signature
        {
            if (_metadataReaderOpt == null)
            {
                throw new NotSupportedException("Metadata not available");
            }

            var sig = _metadataReaderOpt.GetStandaloneSignature(
                (StandaloneSignatureHandle)MetadataTokens.Handle(tkSignature)
                );
            var signature = _metadataReaderOpt.GetBlobBytes(sig.Signature);

            GCHandle pinnedBuffer = GCHandle.Alloc(signature, GCHandleType.Pinned);

            ppvSig = (byte *)pinnedBuffer.AddrOfPinnedObject();
            pcbSig = signature.Length;

#pragma warning disable RS0042 // Do not copy value
            _pinnedBuffers.Add(pinnedBuffer);
#pragma warning restore RS0042 // Do not copy value
            return(0);
        }
Example #8
0
        public static string GetFullAssemblyName(this SRM.AssemblyReference reference, MetadataReader reader)
        {
            string publicKey = "null";

            if (!reference.PublicKeyOrToken.IsNil)
            {
                if ((reference.Flags & AssemblyFlags.PublicKey) != 0)
                {
                    publicKey = CalculatePublicKeyToken(reference.PublicKeyOrToken, reader);
                }
                else
                {
                    publicKey = reader.GetBlobBytes(reference.PublicKeyOrToken).ToHexString(8);
                }
            }
            string properties = "";

            if ((reference.Flags & AssemblyFlags.Retargetable) != 0)
            {
                properties = ", Retargetable=true";
            }
            return($"{reader.GetString(reference.Name)}, " +
                   $"Version={reference.Version}, " +
                   $"Culture={(reference.Culture.IsNil ? "neutral" : reader.GetString(reference.Culture))}, " +
                   $"PublicKeyToken={publicKey}{properties}");
        }
Example #9
0
        //<SnippetReadPdb>
        static string ReadDocumentPath(MetadataReader reader, Document doc)
        {
            BlobReader blob = reader.GetBlobReader(doc.Name);

            // Read path separator character
            var separator = (char)blob.ReadByte();
            var sb        = new StringBuilder(blob.Length * 2);

            // Read path segments
            while (true)
            {
                BlobHandle bh = blob.ReadBlobHandle();

                if (!bh.IsNil)
                {
                    byte[] nameBytes = reader.GetBlobBytes(bh);
                    sb.Append(Encoding.UTF8.GetString(nameBytes));
                }

                if (blob.Offset >= blob.Length)
                {
                    break;
                }

                sb.Append(separator);
            }

            return(sb.ToString());
        }
        private void ReadAssemblyDefinition()
        {
            var definition = reader.GetAssemblyDefinition();

            assemblyName = reader.GetString(definition.Name);
            publicKey    = definition.PublicKey.IsNil ? null : reader.GetBlobBytes(definition.PublicKey);
        }
Example #11
0
        // https://github.com/Microsoft/msbuild/issues/4002
        // https://github.com/dotnet/corefx/issues/34008
        //
        // We do not use AssemblyReference.GetAssemblyName() here because its behavior
        // is different from other code paths with respect to neutral culture. We will
        // get unspecified culture instead of explicitly neutral culture. This in turn
        // leads string comparisons of assembly-name-modulo-version in RAR to false
        // negatives that break its conflict resolution and binding redirect generation.
        private static AssemblyName GetAssemblyName(MetadataReader metadataReader, AssemblyReferenceHandle handle)
        {
            var entry = metadataReader.GetAssemblyReference(handle);

            var assemblyName = new AssemblyName
            {
                Name        = metadataReader.GetString(entry.Name),
                Version     = entry.Version,
                CultureName = metadataReader.GetString(entry.Culture)
            };

            var publicKeyOrToken = metadataReader.GetBlobBytes(entry.PublicKeyOrToken);

            if (publicKeyOrToken != null)
            {
                if (publicKeyOrToken.Length <= 8)
                {
                    assemblyName.SetPublicKeyToken(publicKeyOrToken);
                }
                else
                {
                    assemblyName.SetPublicKey(publicKeyOrToken);
                }
            }

            assemblyName.Flags = (AssemblyNameFlags)(int)entry.Flags;
            return(assemblyName);
        }
        public static PublicKeyToken GetPublicKeyToken(this MetadataReader metadataReader, BlobHandle handle)
        {
            if (handle.IsNil)
            {
                return(PublicKeyToken.Empty);
            }

            var bytes = metadataReader.GetBlobBytes(handle);

            // Strong named assembly
            if (bytes != null && bytes.Length > 8)
            {
                // Get the public key token, which is the last 8 bytes of the SHA-1 hash of the public key
                using (var sha1 = SHA1.Create())
                {
                    var hash = sha1.ComputeHash(bytes);

                    var token = new byte[8];
                    int count = 0;

                    for (int i = hash.Length - 1; i >= hash.Length - 8; i--)
                    {
                        token[count] = hash[i];
                        count++;
                    }

                    return(new PublicKeyToken(ImmutableArray.Create(token)));
                }
            }

            return(new PublicKeyToken(ImmutableArray.Create(bytes)));
        }
Example #13
0
        private static string FormatPublicKeyToken(this MetadataReader metadataReader, BlobHandle handle)
        {
            byte[] bytes = metadataReader.GetBlobBytes(handle);

            if (bytes == null || bytes.Length <= 0)
            {
                return("null");
            }

            if (bytes.Length > 8)  // Strong named assembly
            {
                // Get the public key token, which is the last 8 bytes of the SHA-1 hash of the public key
                using (var sha1 = SHA1.Create())
                {
                    var token = sha1.ComputeHash(bytes);

                    bytes = new byte[8];
                    int count = 0;
                    for (int i = token.Length - 1; i >= token.Length - 8; i--)
                    {
                        bytes[count] = token[i];
                        count++;
                    }
                }
            }

            // Convert bytes to string, but we don't want the '-' characters and need it to be lower case
            return(BitConverter.ToString(bytes)
                   .Replace("-", "")
                   .ToLowerInvariant());
        }
        private void ParseAssemblyDefinition(MetadataReader reader)
        {
            var assembly = reader.GetAssemblyDefinition();

            Name      = reader.GetString(assembly.Name);
            Version   = assembly.Version;
            PublicKey = reader.GetBlobBytes(assembly.PublicKey).ToList();
        }
Example #15
0
        private static bool TryMapPortablePdb(Module module, out MetadataReaderProvider metadataReaderProvider)
        {
            metadataReaderProvider = null;
            MetadataReader rd = null;

            try
            {
                metadataReaderProvider = GetMetadataReaderProvider(module);
                rd = metadataReaderProvider?.GetMetadataReader();
            }
            catch (BadImageFormatException ex) when(ex.Message == "Invalid COR20 header signature.")
            {
                TraceSourceLink("no portable PDB found: " + module.FullyQualifiedName);
                // todo figure out a better way to detect if PDB is portable or classic
                // https://github.com/dotnet/corefx/blob/06b1365d9881ed26a921490d7edd2d4e4de35565/src/System.Reflection.Metadata/src/System/Reflection/Metadata/MetadataReader.cs#L185
            }
            if (rd == null)
            {
                metadataReaderProvider?.Dispose();
                metadataReaderProvider = null;
                return(false);
            }

            TraceSourceLink("found portable PDB for: " + module.FullyQualifiedName);

            // https://github.com/dotnet/symreader-portable/blob/d27c08d6015c4716ced790e34233c0219773ab10/src/Microsoft.DiaSymReader.PortablePdb/Utilities/MetadataUtilities.cs
            var sourceLinkHandles = rd
                                    .GetCustomDebugInformation(EntityHandle.ModuleDefinition)
                                    .Where(r => !r.IsNil)
                                    .Select(rd.GetCustomDebugInformation)
                                    .Where(cdi => !cdi.Value.IsNil && rd.GetGuid(cdi.Kind) == SourceLinkId)
                                    .ToList();

            if (sourceLinkHandles.Count == 0)
            {
                metadataReaderProvider?.Dispose();
                metadataReaderProvider = null;
                return(false);
            }
            var sourceLinkHandle = sourceLinkHandles.First();
            var sourceLink       = SourceLink.Deserialize(rd.GetBlobBytes(sourceLinkHandle.Value));

            var hinstance = (long)Marshal.GetHINSTANCE(module);

            foreach (var dh in rd.Documents)
            {
                if (dh.IsNil)
                {
                    continue;
                }
                var doc = rd.GetDocument(dh);

                var file = rd.GetString(doc.Name);
                SourceMappedPaths[Tuple.Create(hinstance, file)] = sourceLink.GetUrl(file);
            }

            return(true);
        }
Example #16
0
 public static MetadataAssemblyReference GetAssemblyName(this AssemblyReference reference, MetadataReader reader)
 {
     return(new ReaderMetadataAssemblyReference(
                reader.GetString(reference.Name),
                reference.Version,
                reference.Culture.IsNil ? null : reader.GetString(reference.Culture),
                reference.PublicKeyOrToken.IsNil ? null : reader.GetBlobBytes(reference.PublicKeyOrToken),
                reference.Flags));
 }
Example #17
0
 static string CalculatePublicKeyToken(BlobHandle blob, MetadataReader reader)
 {
     // Calculate public key token:
     // 1. hash the public key using the appropriate algorithm.
     byte[] publicKeyTokenBytes = reader.GetHashAlgorithm().ComputeHash(reader.GetBlobBytes(blob));
     // 2. take the last 8 bytes
     // 3. according to Cecil we need to reverse them, other sources did not mention this.
     return(publicKeyTokenBytes.TakeLast(8).Reverse().ToHexString(8));
 }
        static AssemblyName CreateAssemblyName(MetadataReader mdReader, AssemblyReference ar)
        {
            var an = CreateAssemblyName(mdReader, ar.Name, ar.Version, ar.Culture);

            if (!ar.PublicKeyOrToken.IsNil)
            {
                an.SetPublicKeyToken(mdReader.GetBlobBytes(ar.PublicKeyOrToken));
            }
            return(an);
        }
        static AssemblyName CreateAssemblyName(MetadataReader mdReader, AssemblyDefinition ad)
        {
            var an = CreateAssemblyName(mdReader, ad.Name, ad.Version, ad.Culture);

            if (!ad.PublicKey.IsNil)
            {
                an.SetPublicKey(mdReader.GetBlobBytes(ad.PublicKey));
            }
            return(an);
        }
Example #20
0
        public AssemblyName ToAssemblyName(AssemblyReference ar)
        {
            AssemblyName result = new AssemblyName();

            result.CultureInfo = string.IsNullOrEmpty(_metaReader.GetString(ar.Culture)) ? null : new System.Globalization.CultureInfo(_metaReader.GetString(ar.Culture));
            result.Name        = _metaReader.GetString(ar.Name);
            result.Version     = ar.Version;
            result.SetPublicKeyToken(_metaReader.GetBlobBytes(ar.PublicKeyOrToken));

            return(result);
        }
Example #21
0
        public unsafe int GetSigFromToken(int tkSignature, out byte *ppvSig, out int pcbSig)
        {
            var signatureHandle = (StandaloneSignatureHandle)MetadataTokens.Handle(tkSignature);
            var bytes           = MetadataReader.GetBlobBytes(MetadataReader.GetStandaloneSignature(signatureHandle).Signature);

            var pinned = GCHandle.Alloc(bytes, GCHandleType.Pinned);

            ppvSig = (byte *)pinned.AddrOfPinnedObject();
            pcbSig = bytes.Length;
            return(HResult.S_OK);
        }
        public ScannedAssembly(AssemblyReferenceHandle handle, MetadataReader reader)
        {
            var reference = reader.GetAssemblyReference(handle);

            Name             = reader.GetString(reference.Name);
            Culture          = reader.GetString(reference.Culture);
            PublicKey        = reader.GetBlobBytes(reference.PublicKeyOrToken).ToList();
            Token            = reader.GetToken(handle);
            Version          = reference.Version;
            Flags            = reference.Flags;
            ResolutionStatus = ResolutionStatus.UnResolved;
        }
        private byte[]? GetSourceLinkBytes()
        {
            if (_reader == null)
            {
                return(null);
            }
            var blobh = default(BlobHandle);

            foreach (var cdih in _reader.GetCustomDebugInformation(EntityHandle.ModuleDefinition))
            {
                var cdi = _reader.GetCustomDebugInformation(cdih);
                if (_reader.GetGuid(cdi.Kind) == SourceLinkId)
                {
                    blobh = cdi.Value;
                }
            }
            if (blobh.IsNil)
            {
                return(Array.Empty <byte>());
            }
            return(_reader.GetBlobBytes(blobh));
        }
Example #24
0
        internal static AssemblyName GetAssemblyName(MetadataReader metadata, AssemblyReference assembly)
        {
            var  name         = new AssemblyName(metadata.GetString(assembly.Name));
            bool hasPublicKey = (assembly.Flags & AssemblyFlags.PublicKey) != 0;

            if (hasPublicKey)
            {
                name.Flags = AssemblyNameFlags.PublicKey;
                name.SetPublicKey(metadata.GetBlobBytes(assembly.PublicKeyOrToken));
            }
            else
            {
                name.SetPublicKeyToken(metadata.GetBlobBytes(assembly.PublicKeyOrToken));
            }

            name.CultureName = assembly.Culture.IsNil
                ? string.Empty
                : metadata.GetString(assembly.Culture);

            name.Version = assembly.Version;
            return(name);
        }
Example #25
0
        private static AssemblyName GetAssemblyName(MetadataReader metadataReader)
        {
            AssemblyName name = new AssemblyName();

            AssemblyDefinition definition = metadataReader.GetAssemblyDefinition();

            name.Name        = metadataReader.GetString(definition.Name);
            name.Version     = definition.Version;
            name.CultureInfo = CultureInfo.GetCultureInfo(metadataReader.GetString(definition.Culture));
            name.SetPublicKey(metadataReader.GetBlobBytes(definition.PublicKey));

            return(name);
        }
        //TODO: should replace the AssembyName.GetAssemblyVersion with something based on SMR.
        public static AssemblyName GetAssemblyName(MetadataReader metaReader, AssemblyDefinition assemblyDef)
        {
            AssemblyName result = new AssemblyName();

            result.CultureInfo = string.IsNullOrEmpty(metaReader.GetString(assemblyDef.Culture)) ?
                                 null :
                                 new System.Globalization.CultureInfo(metaReader.GetString(assemblyDef.Culture));

            result.Name    = metaReader.GetString(assemblyDef.Name);
            result.Version = assemblyDef.Version;
            result.SetPublicKey(metaReader.GetBlobBytes(assemblyDef.PublicKey));

            return(result);
        }
        private IReadOnlyList <SourceLinkMap> GetSourceLinkInformation()
        {
            var sl = (from cdi in _reader.CustomDebugInformation
                      let cd = _reader.GetCustomDebugInformation(cdi)
                               let kind = _reader.GetGuid(cd.Kind)
                                          where kind == SourceLinkGuid
                                          let bl = _reader.GetBlobBytes(cd.Value)
                                                   select Encoding.UTF8.GetString(bl))
                     .FirstOrDefault();

            if (sl != null)
            {
                try
                {
                    var jobj = JObject.Parse(sl);
                    var docs = (JObject)jobj["documents"];


                    var slis = (from prop in docs.Properties()
                                select new SourceLinkMap
                    {
                        Base = prop.Name,
                        Location = prop.Value.Value <string>()
                    })
                               .ToList();

                    return(slis);
                }
                catch (JsonReaderException jse)
                {
                    throw new InvalidDataException("SourceLink data could not be parsed", jse);
                }
            }

            return(Array.Empty <SourceLinkMap>());
        }
Example #28
0
        Object ResolveAssemblyReference(AssemblyReferenceHandle handle)
        {
            AssemblyReference assemblyReference = _metadataReader.GetAssemblyReference(handle);

            AssemblyName an = new AssemblyName();

            an.Name    = _metadataReader.GetString(assemblyReference.Name);
            an.Version = assemblyReference.Version;

            var publicKeyOrToken = _metadataReader.GetBlobBytes(assemblyReference.PublicKeyOrToken);

            if ((an.Flags & AssemblyNameFlags.PublicKey) != 0)
            {
                an.SetPublicKey(publicKeyOrToken);
            }
            else
            {
                an.SetPublicKeyToken(publicKeyOrToken);
            }

            // TODO: ContentType, Culture - depends on newer version of the System.Reflection contract

            return(Context.ResolveAssembly(an));
        }
Example #29
0
        private IReadOnlyList <SourceLinkMap> GetSourceLinkInformation()
        {
            var sl = (from cdi in _reader.CustomDebugInformation
                      let cd = _reader.GetCustomDebugInformation(cdi)
                               let kind = _reader.GetGuid(cd.Kind)
                                          where kind == SourceLinkGuid
                                          let bl = _reader.GetBlobBytes(cd.Value)
                                                   select Encoding.UTF8.GetString(bl))
                     .FirstOrDefault();

            var jobj = JObject.Parse(sl);
            var docs = (JObject)jobj["documents"];


            var slis = (from prop in docs.Properties()
                        select new SourceLinkMap
            {
                Base = prop.Name,
                Location = prop.Value.Value <string>()
            })
                       .ToList();

            return(slis);
        }
Example #30
0
        private byte[]? TryGetEmbeddedTextBytes(DocumentHandle handle)
        {
            var handles = _pdbReader.GetCustomDebugInformation(handle);

            foreach (var cdiHandle in handles)
            {
                var cdi  = _pdbReader.GetCustomDebugInformation(cdiHandle);
                var guid = _pdbReader.GetGuid(cdi.Kind);
                if (guid == PortableCustomDebugInfoKinds.EmbeddedSource)
                {
                    return(_pdbReader.GetBlobBytes(cdi.Value));
                }
            }

            return(null);
        }
Example #31
0
        /// <summary>
        /// PropertyMap Table Columns:
        ///     Parent (RID to TypeDef)
        ///     PropertyList (RID to EventTable)
        /// ===========================================
        /// Property Table Columns:
        ///     Name (offset to #String)
        ///     PropFlags (2 byte unsigned)
        ///     Type (offset to #blob - Signature)
        /// </summary>
        private void ValidateProperty(MetadataReader reader, uint rowId, uint startIndex, uint count, bool isVBMod = false)
        {
            if (0 == count)
            {
                return;
            }

            // ModuleCS01
            var expNames = new string[]
            {
                "AppProp", "P01", "Item", "P01", "Item",
                "CS1IGoo<System.Linq.Expressions.Expression,System.Object>.P01",
                "CS1IGoo<System.Linq.Expressions.Expression,System.Object>.Item",
            };
            var expSigs = new byte[][]
            {
                new byte[] { 0x28, 00, 0x15, 0x12, 0x21, 0x02, 0x12, 0x19, 0x1c }, new byte[] { 0x28, 00, 0x13, 00 },
                new byte[] { 0x28, 01, 0x1c, 0x13, 00 }, new byte[] { 0x28, 0x00, 0x13, 00 }, new byte[] { 0x28, 0x01, 0x1c, 0x13, 00 },
                new byte[] { 0x28, 00, 0x12, 0x19 }, new byte[] { 0x28, 01, 0x1c, 0x12, 0x19 }
            };

            // ModuleVB01
            // Prop: 0:0000, 1:string#13c, 2:blob#70 | 0:0000, 1:string#14d, 2:blob#75
            var modNames = new string[]
            {
                "ModVBDefaultProp", "ModVBProp",
            };
            var modSigs = new byte[][]
            {
                new byte[] { 0x28, 01, 0x0e, 0x08 }, new byte[] { 0x28, 00, 0x11, 0x09 },
            };

            // Validity Rules
            uint zeroBased = startIndex - 1;
            uint delta = count;

            // Last one
            if (0xF0000000 == count)
            {
                delta = (uint)reader.PropertyTable.NumberOfRows - zeroBased;
                if (0 == delta)
                {
                    return;
                }
            }

            Assert.InRange((uint)reader.PropertyTable.NumberOfRows, zeroBased + count, uint.MaxValue);
            for (uint i = zeroBased; i < zeroBased + count; i++)
            {
                var handle = PropertyDefinitionHandle.FromRowId((int)i + 1);
                var row = reader.GetPropertyDefinition(handle);

                // Name
                if (isVBMod)
                {
                    Assert.Equal(modNames[i], reader.GetString(row.Name));
                }
                else
                {
                    Assert.Equal(expNames[i], reader.GetString(row.Name));
                }

                Assert.Equal(0, (ushort)row.Attributes);

                var sig = reader.GetBlobBytes(row.Signature);
                Assert.Equal(40, sig[0]);
                byte[] exp;
                if (isVBMod)
                {
                    exp = modSigs[i];
                }
                else
                {
                    exp = expSigs[i];
                }

                for (int j = 0; j < exp.Length; j++)
                {
                    Assert.Equal(exp[j], sig[j]);
                }
            } // for
        }
Example #32
0
        /// <summary>
        /// Method Table Columns:
        ///     Name (offset to #String)
        ///     Flags, ImplFlags (2 byte unsigned)
        ///     Signature (offset to #blob)
        ///     ParamList (RID to Param)
        ///     RVA (4-byte unsigned) -> body
        /// </summary>
        private void ValidateMethodDef(MetadataReader reader, uint startIndex, uint count, bool isMod = false)
        {
            if (0 == count)
            {
                return;
            }

            var expNames = new string[]
            {
                "get_AppProp", ".ctor", "AppMethod", ".cctor", "get_Item",
                "Use", ".ctor", "set_ContraFooProp", "CoFooMethod", "NormalFoo",
                "set_ContraFooProp", ".ctor", "CoFooMethod", ".ctor", "NormalFoo",
                ".ctor", ".ctor", ".ctor", "Main", ".ctor",
            };
            var expFlags = new ushort[]
            {
                0x0883, 0x1886, 0x0084, 0x1891, 0x0881,   0x0086, 0x1886, 0x0dc6, 0x05c6, 0x05c6,
                    0x09e6, 0x1886, 0x01e6, 0x1886, 0x01e6, 0x1886, 0x1886, 0x1886, 0x0096, 0x1886
                };
            var expRVAs = new uint[]
            {
                0x2050, 0x2070, 0x20a4, 0x20b7, 0x20c0, 0x20d4, 0x2105, 0, 0, 0,
                0x2115, 0x2118, 0x2120, 0x2152, 0x215c, 0x2177, 0x217f, 0x2187, 0x2190, 0x21d5
            };

            var expSigs = new byte[][]
            {
                new byte[] { 0x20, 0x00, 0x15, 0x12, 0x15, 0x02, 0x12, 0x19, 0x1c }, new byte[] { 0x20, 01, 01, 0x10, 0x12, 0x1d },
                new byte[] { 0x30, 01, 01, 0x15, 0x12, 0x21, 0x01, 0x1e, 00, 0x1e, 00 }, new byte[] { 0x00, 0x00, 0x01 },
                new byte[] { 0x20, 01, 0x11, 0x29, 0x11, 0x29 }, new byte[] { 0x20, 00, 0x15, 0x12, 0x21, 0x01, 0x12, 0x35 },
                new byte[] { 0x20, 00, 01 }, new byte[] { 0x20, 01, 01, 0x13, 00 },
                new byte[] { 0x20, 00, 0x13, 00 }, new byte[] { 0x20, 01, 0x13, 00, 0x13, 00 },
                new byte[] { 0x20, 01, 01, 0x13, 00 }, new byte[] { 0x20, 00, 01 },
                new byte[] { 0x20, 00, 0x13, 00 }, new byte[] { 0x20, 00, 01 },
                new byte[] { 0x20, 01, 0x13, 00, 0x13, 00 }, new byte[] { 0x20, 00, 01 },
                new byte[] { 0x20, 00, 01 }, new byte[] { 0x20, 00, 01 }, new byte[] { 00, 00, 08 }, new byte[] { 0x20, 00, 01 },
            };

            var modNames = new string[]
            {
                ".ctor", "get_ModVBDefaultProp", "set_ModVBDefaultProp", "get_ModVBProp", "BCSub01",
                "BCFunc02", ".cctor", "add_AnEvent", "remove_AnEvent", "EventHandler1",
                "BSFunc01", ".ctor", "BeginInvoke", "EndInvoke", "Invoke",
            };
            var modFlags = new ushort[]
            {
                0x1806, 0x0803, 0x0803, 0x0806, 0x0006,
                0x0006, 0x1811, 0x0806, 0x0806, 0x0006, 0x0006, 0x1806, 0x0346, 0x0346, 0x0346,
                };
            var modImpls = new ushort[]
            {
                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 3, 3, 3,
            };
            var modRVAs = new uint[]
            {
                0x2050, 0x2058, 0x2070, 0x2074, 0x2090,
                    0x20a8, 0x20bc, 0x20cc, 0x20e8, 0x2104,  0x2108, 0, 0, 0, 0
            };
            var modSigs = new byte[][]
            {
                new byte[] { 0x20, 0x00, 0x01 }, new byte[] { 0x20, 01, 0x0e, 0x08 },
                new byte[] { 0x20, 02, 01, 0x08, 0x0e }, new byte[] { 0x20, 00, 0x11, 0x09 },
                new byte[] { 0x20, 02, 01, 0x11, 0x0d, 0x12, 0x11 }, new byte[] { 0x20, 01, 0x12, 0x15, 0x10, 0x12, 0x19 },
                new byte[] { 0x00, 00, 01 }, new byte[] { 0x20, 01, 01, 0x12, 0x18 },
                new byte[] { 0x20, 01, 01, 0x12, 0x18 }, new byte[] { 0x20, 02, 01, 0x1c, 0x12, 0x21 },
                new byte[] { 0x20, 01, 0x1c, 0x10, 0x11, 0x14 }, new byte[] { 0x20, 02, 01, 0x1c, 0x18 },
                new byte[] { 0x20, 04, 0x12, 0x2d, 0x1c, 0x12, 0x21, 0x12, 0x31, 0x1c }, new byte[] { 0x20, 01, 01, 0x12, 0x2d },
                new byte[] { 0x20, 02, 01, 0x1c, 0x12, 0x21 },
            };

            if (startIndex > reader.MethodDefTable.NumberOfRows)
            {
                return;
            }

            uint zeroBased = startIndex - 1;
            uint delta = count;

            // Last one
            if (0xF0000000 == count)
            {
                delta = (uint)reader.MethodDefTable.NumberOfRows - zeroBased;
                if (0 == delta)
                {
                    return;
                }
            }

            Assert.InRange((uint)reader.MethodDefTable.NumberOfRows, zeroBased + delta, uint.MaxValue); // 1 based
            bool first = true;
            uint prevParamStart = 0;
            for (uint i = zeroBased; i < zeroBased + delta; i++)
            {
                var handle = MethodDefinitionHandle.FromRowId((int)i + 1);
                var flags = reader.MethodDefTable.GetFlags(handle);
                var implFlags = reader.MethodDefTable.GetImplFlags(handle);
                var rva = reader.MethodDefTable.GetRva(handle);
                var name = reader.MethodDefTable.GetName(handle);
                var signature = reader.MethodDefTable.GetSignature(handle);
                var paramStart = (uint)reader.MethodDefTable.GetParamStart((int)i + 1);

                if (isMod)
                {
                    // Console.WriteLine("M: {0}", reader.GetString(row.Name));
                    Assert.Equal(modNames[i], reader.GetString(name));

                    Assert.Equal(modFlags[i], (ushort)flags);
                    Assert.Equal(modImpls[i], (ushort)implFlags);
                    Assert.Equal(modRVAs[i], (uint)rva);
                }
                else
                {
                    // Console.WriteLine("M: {0}", reader.GetString(row.Name));
                    Assert.Equal(expNames[i], reader.GetString(name));

                    Assert.Equal(expFlags[i], (ushort)flags);
                    Assert.Equal((ushort)0, (ushort)implFlags);
                    Assert.Equal(expRVAs[i], (uint)rva);
                }

                var sig = reader.GetBlobBytes(signature);
                int len = 0;
                if (isMod)
                {
                    len = modSigs[i].Length;
                }
                else
                {
                    len = expSigs[i].Length;
                }

                for (int j = 0; j < len; j++)
                {
                    if (isMod)
                    {
                        Assert.Equal(modSigs[i][j], sig[j]);
                    }
                    else
                    {
                        Assert.Equal(expSigs[i][j], sig[j]);
                    }
                }

                // validate previous row's param as it needs current row's other to calc how many
                if (!first)
                {
                    ValidateParam(reader, prevParamStart, paramStart - prevParamStart, isMod);
                }

                // Last
                if (i + 1 == reader.MethodDefTable.NumberOfRows)
                {
                    ValidateParam(reader, paramStart, 0xF0000000, isMod);
                }

                prevParamStart = paramStart;
                first = false;
            }
        }
Example #33
0
        /// <summary>
        /// Field Table Columns:
        ///     Name (offset to #String)
        ///     Flags (2 byte unsigned)
        ///     Signature (offset to #blob)
        /// </summary>
        private void ValidateFieldDef(MetadataReader reader, uint startIndex, uint count, bool isMod = false)
        {
            if (count == 0)
            {
                return;
            }

            // APPCS
            var expNames = new string[] { "AppField01", "AppField02" };
            var expFlags = new FieldAttributes[]
            {
                /*0x11*/
                         FieldAttributes.Private | FieldAttributes.Static,
                /*0x01*/ FieldAttributes.Private,
                };
            var expSigs = new byte[][] { new byte[] { 0x06, 0x12, 0x11 }, new byte[] { 0x06, 0x12, 0x25 }, };

            // =====================================================================================================
            // VB Module - 8
            var modNames = new string[] { "ConstString", "ArrayField", "AnEventEvent", "value__", "None", "Red", "Yellow", "Blue", };
            var modFlags = new FieldAttributes[]
            {
                /* 0x8053 */
                             FieldAttributes.HasDefault | FieldAttributes.Literal | FieldAttributes.Static | FieldAttributes.FamANDAssem | FieldAttributes.Private,
                /* 0x0016 */ FieldAttributes.Static | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                /* 0x0001 */ FieldAttributes.Private,
                /* 0x0606 */ FieldAttributes.RTSpecialName | FieldAttributes.SpecialName | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                /* 0x8056 */ FieldAttributes.HasDefault | FieldAttributes.Literal | FieldAttributes.Static | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                /* 0x8056 */ FieldAttributes.HasDefault | FieldAttributes.Literal | FieldAttributes.Static | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                /* 0x8056 */ FieldAttributes.HasDefault | FieldAttributes.Literal | FieldAttributes.Static | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                /* 0x8056 */ FieldAttributes.HasDefault | FieldAttributes.Literal | FieldAttributes.Static | FieldAttributes.Family | FieldAttributes.FamANDAssem,
                };
            var modSigs = new byte[][]
            {
                new byte[] { 0x06, 0x0e }, new byte[] { 0x06, 0x14, 0x11, 0x14, 02, 00, 02, 00, 00 },
                new byte[] { 0x06, 0x12, 0x18 }, new byte[] { 0x06, 0x08 },
                new byte[] { 0x06, 0x11, 0x10 }, new byte[] { 0x06, 0x11, 0x10 },
                new byte[] { 0x06, 0x11, 0x10 }, new byte[] { 0x06, 0x11, 0x10 },
            };

            if (startIndex > reader.FieldTable.NumberOfRows)
            {
                return;
            }

            uint zeroBased = startIndex - 1;
            uint delta = count;

            // Last one
            if (0xF0000000 == count)
            {
                delta = (uint)reader.FieldTable.NumberOfRows - zeroBased;
                if (0 == delta)
                {
                    return;
                }
            }

            Assert.InRange((uint)reader.FieldTable.NumberOfRows, zeroBased + delta, uint.MaxValue); // 1 based
            for (uint i = zeroBased; i < zeroBased + delta; i++)
            {
                var handle = FieldDefinitionHandle.FromRowId((int)(i + 1));
                var row = reader.GetFieldDefinition(handle);

                if (isMod)
                {
                    Assert.Equal(modNames[i], reader.GetString(row.Name));
                    Assert.Equal(modFlags[i], row.Attributes);
                }
                else
                {
                    Assert.Equal(expNames[i], reader.GetString(row.Name));
                    Assert.Equal(expFlags[i], row.Attributes);
                }

                var sig = reader.GetBlobBytes(row.Signature);

                // calling convention, always 6 for field
                Assert.Equal(sig[0], 6);
                int len = 0;
                if (isMod)
                {
                    len = modSigs[i].Length;
                }
                else
                {
                    len = expSigs[i].Length;
                }

                for (int j = 1; j < len; j++)
                {
                    if (isMod)
                    {
                        Assert.Equal(modSigs[i][j], sig[j]);
                    }
                    else
                    {
                        Assert.Equal(expSigs[i][j], sig[j]);
                    }
                }
            }
        }