Beispiel #1
0
        public byte[] GetStreamBytes(BinaryReader reader, StreamHeader streamHeader, uint metadataDirectoryAddress, IEnumerable <Section> sections)
        {
            var rva        = metadataDirectoryAddress + streamHeader.Offset;
            var fileOffset = BinUtil.RVAToOffset(rva, sections);

            reader.BaseStream.Seek((long)fileOffset, SeekOrigin.Begin);
            return(reader.ReadBytes((int)streamHeader.Size));
        }
Beispiel #2
0
        private static byte[] ReadStrongNameHash(BinaryReader reader, uint rva, uint size, IEnumerable <Section> sections)
        {
            if (rva == 0)
            {
                return(new byte[0]);
            }

            var fileOffset = BinUtil.RVAToOffset(rva, sections);

            reader.BaseStream.Seek((long)fileOffset, SeekOrigin.Begin);
            return(reader.ReadBytes((int)size));
        }
Beispiel #3
0
        private void Init(byte[] data)
        {
            #region Parse PE Header
            RawFile = new BinaryReader(new MemoryStream(data));
            BinaryReader r = new BinaryReader(new MemoryStream(data));

            DosHeader = ReadDOSHeader(r);
            PeHeader  = ReadPEHeader(DosHeader.COFFHeaderAddress, r);

            //Read all of the data
            PeHeader.Directories = ReadDirectoriesList(PeHeader.DirectoryLength, r);
            PeHeader.Sections    = ReadSectionsList(PeHeader.NumberOfSections, r);
            #endregion
            #region Parse Clr header & Strong name hash
            try
            {
                ClrHeader = ReadCLRHeader(r, PeHeader);
            }
            catch
            {
                Console.WriteLine("No clr header!");
                ContainsMetadata = false;
                return;
            }

            //Read the strong name hash
            ClrStrongNameHash = ReadStrongNameHash(r, ClrHeader.StrongNameSignatureAddress, ClrHeader.StrongNameSignatureSize, PeHeader.Sections);
            #endregion
            #region Parse Metadata header

            //Skip past all of the IL Code, and get tto the metadata header
            long pos = (long)BinUtil.RVAToOffset(ClrHeader.MetaDataDirectoryAddress, PeHeader.Sections);
            r.BaseStream.Position = pos;


            ClrMetaDataHeader                     = new MetadataHeader();
            ClrMetaDataHeader.Signature           = r.ReadUInt32();
            ClrMetaDataHeader.MajorVersion        = r.ReadUInt16();
            ClrMetaDataHeader.MinorVersion        = r.ReadUInt16();
            ClrMetaDataHeader.Reserved1           = r.ReadUInt32();
            ClrMetaDataHeader.VersionStringLength = r.ReadUInt32();
            ClrMetaDataHeader.VersionString       = r.ReadNullTermString((int)ClrMetaDataHeader.VersionStringLength);
            ClrMetaDataHeader.Flags               = r.ReadUInt16(); //reserved
            ClrMetaDataHeader.NumberOfStreams     = r.ReadUInt16();

            //Simple checks
            //Debug.Assert(ClrMetaDataHeader.Signature == 0x424A5342);
            //Debug.Assert(ClrMetaDataHeader.Reserved1 == 0);
            //Debug.Assert(ClrMetaDataHeader.Flags == 0);
            #endregion
            #region Parse Streams

            //Parse the StreamHeader(s)
            for (int i = 0; i < ClrMetaDataHeader.NumberOfStreams; i++)
            {
                var hdr = new StreamHeader();

                hdr.Offset = r.ReadUInt32();
                hdr.Size   = r.ReadUInt32();
                hdr.Name   = r.ReadNullTermFourByteAlignedString();

                Streams.Add(hdr);
            }

            //Parse the #String stream
            var bytes = GetStreamBytes("#Strings", r);
            ClrStringsStream = new StringsStream(bytes);

            //Parse the #US Stream
            var bytes2 = GetStreamBytes("#US", r);
            //File.WriteAllBytes("strings", bytes2);
            ClrUsStream = new USStreamReader(bytes2).Read();


            #endregion
            #region Parse #~ Stream aka Tabels stream
            //Parse the #~ stream
            BinaryReader TableStreamR = new BinaryReader(new MemoryStream(GetStreamBytes("#~", r)));
            ClrMetaDataStreamHeader = ReadHeader(TableStreamR);

            //Parse the tabels data
            var numberOfTables = GetTableCount(ClrMetaDataStreamHeader.TablesFlags);
            ClrMetaDataStreamHeader.TableSizes = new uint[numberOfTables];

            for (var i = 0; i < numberOfTables; i++)
            {
                ClrMetaDataStreamHeader.TableSizes[i] = TableStreamR.ReadUInt32();
            }

            MetadataReader = new MetadataReader(TableStreamR.BaseStream);
            BlobStream     = GetStreamBytes("#Blob", r);

            //Parse the tabels
            Tabels = new Tabels(this);
            #endregion
        }