Beispiel #1
0
		/// <summary>
		/// Creates a <see cref="HotStream"/> instance
		/// </summary>
		/// <param name="version">Hot heap version</param>
		/// <param name="imageStream">Heap stream</param>
		/// <param name="streamHeader">Stream header info</param>
		/// <param name="fullStream">Stream for the full PE file</param>
		/// <param name="baseOffset">Offset in <paramref name="fullStream"/> where the data starts</param>
		/// <returns>A <see cref="HotStream"/> instance or <c>null</c> if <paramref name="version"/>
		/// is invalid</returns>
		public static HotStream Create(HotHeapVersion version, IImageStream imageStream, StreamHeader streamHeader, IImageStream fullStream, FileOffset baseOffset) {
			switch (version) {
			case HotHeapVersion.CLR20: return new HotStreamCLR20(imageStream, streamHeader, fullStream, baseOffset);
			case HotHeapVersion.CLR40: return new HotStreamCLR40(imageStream, streamHeader, fullStream, baseOffset);
			default: return null;
			}
		}
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			setOffsetCalled = true;
			this.offset = offset;
			this.rva = rva;

			tinyMethodsDict = null;
			fatMethodsDict = null;

			var rva2 = rva;
			foreach (var mb in tinyMethods) {
				mb.SetOffset(offset, rva2);
				uint len = mb.GetFileLength();
				rva2 += len;
				offset += len;
			}

			foreach (var mb in fatMethods) {
				if (alignFatBodies) {
					uint padding = (uint)rva2.AlignUp(FAT_BODY_ALIGNMENT) - (uint)rva2;
					rva2 += padding;
					offset += padding;
				}
				mb.SetOffset(offset, rva2);
				uint len = mb.GetFileLength();
				rva2 += len;
				offset += len;
			}

			length = (uint)rva2 - (uint)rva;
		}
		/// <summary>
		/// Returns the first <see cref="ImageSectionHeader"/> that has data at file offset
		/// <paramref name="offset"/>
		/// </summary>
		/// <param name="offset">The file offset</param>
		/// <returns></returns>
		public ImageSectionHeader ToImageSectionHeader(FileOffset offset) {
			foreach (var section in imageSectionHeaders) {
				if ((long)offset >= section.PointerToRawData && (long)offset < section.PointerToRawData + section.SizeOfRawData)
					return section;
			}
			return null;
		}
Beispiel #4
0
		/// <summary>
		/// Constructor
		/// </summary>
		/// <param name="fileOffset">File offset of data</param>
		/// <param name="data">The data</param>
		/// <param name="dataOffset">Start offset in <paramref name="data"/></param>
		/// <param name="dataLength">Length of data</param>
		public MemoryImageStream(FileOffset fileOffset, byte[] data, int dataOffset, int dataLength) {
			this.fileOffset = fileOffset;
			this.data = data;
			this.dataOffset = dataOffset;
			this.dataEnd = dataOffset + dataLength;
			this.position = dataOffset;
		}
		/// <summary>
		/// Constructor
		/// </summary>
		/// <param name="owner">Owner of memory</param>
		/// <param name="fileOffset">File offset of data</param>
		/// <param name="baseAddr">Address of data</param>
		/// <param name="length">Length of data</param>
		public unsafe UnmanagedMemoryImageStream(UnmanagedMemoryStreamCreator owner, FileOffset fileOffset, long baseAddr, long length) {
			this.fileOffset = fileOffset;
			this.startAddr = baseAddr;
			this.endAddr = baseAddr + length;
			this.currentAddr = this.startAddr;
			this.owner = owner;
		}
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			this.offset = offset;
			this.rva = rva;

			padding = rva.AlignUp(4) - rva + 2;
			length = padding + 6;
		}
		/// <inheritdoc/>
		public unsafe IImageStream Create(FileOffset offset, long length) {
			if ((long)offset < 0 || length < 0)
				return MemoryImageStream.CreateEmpty();

			long offs = Math.Min(Length, (long)offset);
			long len = Math.Min(Length - offs, length);
			return new UnmanagedMemoryImageStream(owner, (FileOffset)((long)fileOffset + (long)offset), startAddr + (long)offs, len);
		}
Beispiel #8
0
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			this.offset = offset;
			this.rva = rva;

			length = HEADER_SIZE;
			if (data != null)	// Could be null if dontWriteAnything is true
				length += (uint)data.Length;
		}
		/// <inheritdoc/>
		public IImageStream Create(FileOffset offset, long length) {
			if (offset < 0 || length < 0)
				return MemoryImageStream.CreateEmpty();

			int offs = (int)Math.Min((long)dataLength, (long)offset);
			int len = (int)Math.Min((long)dataLength - offs, length);
			return new MemoryImageStream(offset, data, dataOffset + offs, len);
		}
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			setOffsetCalled = true;
			this.offset = offset;
			this.rva = rva;
			foreach (var resource in resources) {
				resource.SetOffset(offset + 4, rva + 4);
				uint len = 4 + resource.GetFileLength();
				offset = (offset + len).AlignUp(alignment);
				rva = (rva + len).AlignUp(alignment);
			}
		}
Beispiel #11
0
		public CilBodyOptions(CilBody body, RVA rva, FileOffset fileOffset)
		{
			this.KeepOldMaxStack = body.KeepOldMaxStack;
			this.InitLocals = body.InitLocals;
			this.MaxStack = body.MaxStack;
			this.LocalVarSigTok = body.LocalVarSigTok;
			this.RVA = rva;
			this.FileOffset = fileOffset;
			this.Instructions.AddRange(body.Instructions);
			this.ExceptionHandlers.AddRange(body.ExceptionHandlers);
			this.Locals.AddRange(body.Variables);
			this.Scope = body.Scope;
		}
		/// <summary>
		/// Returns the <see cref="FileOffset"/> and <see cref="RVA"/> of a
		/// <see cref="ResourceDirectoryEntry"/>. <see cref="SetOffset"/> must have been called.
		/// </summary>
		/// <param name="dirEntry">A <see cref="ResourceDirectoryEntry"/></param>
		/// <param name="fileOffset">Updated with the file offset</param>
		/// <param name="rva">Updated with the RVA</param>
		/// <returns><c>true</c> if <paramref name="dirEntry"/> is valid and
		/// <paramref name="fileOffset"/> and <paramref name="rva"/> have been updated. <c>false</c>
		/// if <paramref name="dirEntry"/> is not part of the Win32 resources.</returns>
		public bool GetFileOffsetAndRvaOf(ResourceDirectoryEntry dirEntry, out FileOffset fileOffset, out RVA rva) {
			var dir = dirEntry as ResourceDirectory;
			if (dir != null)
				return GetFileOffsetAndRvaOf(dir, out fileOffset, out rva);

			var dataHeader = dirEntry as ResourceData;
			if (dataHeader != null)
				return GetFileOffsetAndRvaOf(dataHeader, out fileOffset, out rva);

			fileOffset = 0;
			rva = 0;
			return false;
		}
Beispiel #13
0
		public CilBodyOptions(CilBody body, RVA headerRva, FileOffset headerFileOffset, RVA rva, FileOffset fileOffset) {
			KeepOldMaxStack = body.KeepOldMaxStack;
			InitLocals = body.InitLocals;
			HeaderSize = body.HeaderSize;
			MaxStack = body.MaxStack;
			LocalVarSigTok = body.LocalVarSigTok;
			HeaderRVA = headerRva;
			HeaderFileOffset = headerFileOffset;
			RVA = rva;
			FileOffset = fileOffset;
			Instructions.AddRange(body.Instructions);
			ExceptionHandlers.AddRange(body.ExceptionHandlers);
			Locals.AddRange(body.Variables);
			Scope = body.Scope;
		}
Beispiel #14
0
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			this.offset = offset;
			this.rva = rva;

			length = 0x28;
			importLookupTableRVA = rva + length;
			length += 8;

			stringsPadding = (int)(rva.AlignUp(STRINGS_ALIGNMENT) - rva);
			length += (uint)stringsPadding;
			corXxxMainRVA = rva + length;
			length += 0xE;
			mscoreeDllRVA = rva + length;
			length += 0xC;
			length++;
		}
Beispiel #15
0
 /// <summary>
 /// Add a read being parsed to the index
 /// </summary>
 /// <param name="alignedSequence"></param>
 /// <param name="offset"></param>
 internal void AddReadToIndexInformation(SAM.SAMAlignedSequence alignedSequence, FileOffset offset)
 {
     if (offset < FirstOffSetSeen) { FirstOffSetSeen = offset; }
     else if (offset > LastOffSetSeen) { LastOffSetSeen = offset; }            
     //update meta-data
     if (alignedSequence.Pos < 1 || (alignedSequence.Flag&SAMFlags.UnmappedQuery)==SAMFlags.UnmappedQuery)
     {
         UnMappedReadsCount++;
         return;
     }
     else
     {
         MappedReadsCount++;
     }
     //update linear index
     LinearIndexMaker.UpdateLinearArrayIndex(alignedSequence, offset);
 }
Beispiel #16
0
		/// <inheritdoc/>
		public RVA ToRVA(FileOffset offset) {
			return peType.ToRVA(peInfo, offset);
		}
 /// <inheritdoc/>
 public virtual void SetOffset(FileOffset offset, RVA rva)
 {
     this.offset = offset;
     this.rva    = rva;
 }
		/// <summary>
		/// Set <see cref="size"/> according to <paramref name="reader"/>'s current position
		/// </summary>
		/// <param name="reader">The reader</param>
		protected void SetEndoffset(IImageStream reader) {
			size = (uint)(reader.Position - startOffset);
			startOffset = reader.FileOffset + (long)startOffset;
		}
		/// <inheritdoc/>
		public void SetOffset(FileOffset offset, RVA rva) {
			this.offset = offset;
			this.rva = rva;
			//TODO:
		}
Beispiel #20
0
 /// <summary>
 /// Update the linear index array based on an aligned read and its current coordinates
 /// </summary>
 /// <param name="alignedSeq"></param>
 /// <param name="offset"></param>
 internal void UpdateLinearArrayIndex(SAMAlignedSequence alignedSeq, FileOffset offset)
 {
     int pos = alignedSeq.Pos > 0 ? alignedSeq.Pos - 1 : 0;
     int end = alignedSeq.RefEndPos > 0 ? alignedSeq.RefEndPos - 1 : 0;
     pos = pos >> 14;
     end = end >> 14;
     if (end > largestBinSeen) {largestBinSeen = end;}
     for (int i = pos; i <= end; i++)
     {
         var cur = offSetArray[i];
         //TODO: Is second check necessary?  Seems to always be true as we are doing things in order
         if (cur.BothDataElements == 0 || cur > offset) {
             offSetArray[i] = offset;
         }
     }
 }
Beispiel #21
0
			/// <inheritdoc/>
			public RVA ToRVA(PEInfo peInfo, FileOffset offset) {
				return peInfo.ToRVA(offset);
			}
Beispiel #22
0
 /// <summary>
 /// Creates a stream that can access all data starting from <paramref name="offset"/>
 /// </summary>
 /// <param name="self">this</param>
 /// <param name="offset">Offset within the original data</param>
 /// <returns>A new stream</returns>
 public static IImageStream Create(this IImageStreamCreator self, FileOffset offset)
 {
     return(self.Create(offset, long.MaxValue));
 }
		/// <summary>
		/// Calculates <see cref="RVA"/> and <see cref="FileOffset"/> of all <see cref="IChunk"/>s
		/// </summary>
		/// <param name="chunks">All chunks</param>
		/// <param name="offset">Starting file offset</param>
		/// <param name="rva">Starting RVA</param>
		/// <param name="fileAlignment">File alignment</param>
		/// <param name="sectionAlignment">Section alignment</param>
		protected void CalculateRvasAndFileOffsets(List<IChunk> chunks, FileOffset offset, RVA rva, uint fileAlignment, uint sectionAlignment) {
			foreach (var chunk in chunks) {
				chunk.SetOffset(offset, rva);
				offset += chunk.GetFileLength();
				rva += chunk.GetVirtualSize();
				offset = offset.AlignUp(fileAlignment);
				rva = rva.AlignUp(sectionAlignment);
			}
		}
Beispiel #24
0
 /// <inheritdoc />
 public RVA ToRVA(PEInfo peInfo, FileOffset offset)
 {
     return((RVA)offset);
 }
 public RVA ToRVA(PEInfo peInfo, FileOffset offset) => peInfo.ToRVA(offset);
 public RVA ToRVA(PEInfo peInfo, FileOffset offset) => (RVA)offset;
        protected override Task <IEnumerable <Event> > DoSchedule(DiagnosticsSource source)
        {
            TheTrace.TraceInformation("IisBlobScheduler - Starting scheduling");
            var account    = CloudStorageAccount.Parse(source.ConnectionString);
            var client     = account.CreateCloudBlobClient();
            var pathFormat = source.GetProperty <string>("BlobPathFormat");

            TheTrace.TraceInformation("IisBlobScheduler - pathformat: {0}", pathFormat);
            pathFormat = pathFormat.TrimEnd('/') + "/"; // ensure path ends with /

            var offset = FileOffset.Parse(source.LastOffsetPoint);

            if (offset == null)
            {
                throw new InvalidOperationException("FileOffset failed parsing: => " + source.LastOffsetPoint);
            }
            int            instanceIndex = 0;
            DateTimeOffset maxOffset     = offset.TimeOffset;
            FileOffset     newOffset     = null;
            var            events        = new List <Event>();

            while (true)
            {
                bool found = false;

                var path             = string.Format(pathFormat, instanceIndex);
                var isSingleInstance = path == pathFormat;


                TheTrace.TraceInformation("IisBlobScheduler - Looking into {0}", path);
                foreach (var blob in client.ListBlobs(path).Where(itm => itm is CloudBlockBlob)
                         .Cast <CloudBlockBlob>().OrderBy(x => x.Properties.LastModified))
                {
                    if (blob.Properties.LastModified > offset.TimeOffset)
                    {
                        var filename = blob.Uri.ToString();
                        if (!found) // first time running
                        {
                            newOffset = new FileOffset(filename,
                                                       blob.Properties.LastModified ?? DateTimeOffset.UtcNow, blob.Properties.Length);
                        }

                        TheTrace.TraceInformation("IisBlobScheduler - found {0}", blob.Uri);
                        found = true;
                        events.Add(new Event(new BlobFileArrived()
                        {
                            Source      = source.ToSummary(),
                            BlobId      = filename,
                            Position    = (filename == offset.FileName) ? offset.Position : 0, // if same file then pass offset
                            EndPosition = blob.Properties.Length
                        }));
                    }
                }

                if (!found || isSingleInstance)
                {
                    TheTrace.TraceInformation("IisBlobScheduler - Breaking out with index of {0}", instanceIndex);
                    break;
                }

                instanceIndex++;
            }

            source.LastOffsetPoint = newOffset == null?offset.ToString() : newOffset.ToString();

            return(Task.FromResult((IEnumerable <Event>)events));
        }
 void IChunk.SetOffset(FileOffset offset, RVA rva) => throw new NotSupportedException();
Beispiel #29
0
		/// <inheritdoc/>
		public IImageStream CreateStream(FileOffset offset) {
			if ((long)offset > imageStreamCreator.Length)
				throw new ArgumentOutOfRangeException("offset");
			long length = imageStreamCreator.Length - (long)offset;
			return CreateStream(offset, length);
		}
Beispiel #30
0
		/// <inheritdoc/>
		public IImageStream CreateStream(FileOffset offset, long length) {
			return imageStreamCreator.Create(offset, length);
		}
Beispiel #31
0
 /// <inheritdoc />
 public RVA ToRVA(PEInfo peInfo, FileOffset offset)
 {
     return(peInfo.ToRVA(offset));
 }
Beispiel #32
0
			/// <inheritdoc/>
			public RVA ToRVA(PEInfo peInfo, FileOffset offset) {
				return (RVA)offset;
			}
Beispiel #33
0
 /// <inheritdoc />
 public IImageStream CreateStream(FileOffset offset, long length)
 {
     return(imageStreamCreator.Create(offset, length));
 }
Beispiel #34
0
            /// <summary>
            /// Called after all the data has been added
            /// </summary>
            internal List<FileOffset> Freeze()
            {
                if (largestBinSeen != 0)
                {
                    Array.Resize(ref offSetArray, largestBinSeen + 1);
                    FileOffset lastOffSetSeen = new FileOffset();
                    for (int i = 0; i < offSetArray.Length; i++)
                    {
                        if (offSetArray[i].BothDataElements == 0)
                        {
                            offSetArray[i] = lastOffSetSeen;
                        }
                        else { lastOffSetSeen = offSetArray[i]; }
                    }
                }
                else {
                    Array.Resize(ref offSetArray, 0);

                }
                return offSetArray.ToList();
            }       
Beispiel #35
0
 /// <inheritdoc />
 public RVA ToRVA(FileOffset offset)
 {
     return(peType.ToRVA(peInfo, offset));
 }
Beispiel #36
0
 private static void Align(ref FileOffset offset, ref RVA rva)
 {
     offset = offset.AlignUp(HH_ALIGNMENT);
     rva    = rva.AlignUp(HH_ALIGNMENT);
 }
Beispiel #37
0
		static void Align(ref FileOffset offset, ref RVA rva) {
			offset = offset.AlignUp(HH_ALIGNMENT);
			rva = rva.AlignUp(HH_ALIGNMENT);
		}
		/// <summary>
		/// Set <see cref="startOffset"/> to <paramref name="reader"/>'s current position
		/// </summary>
		/// <param name="reader">The reader</param>
		protected void SetStartOffset(IImageStream reader) {
			startOffset = (FileOffset)reader.Position;
		}
Beispiel #39
0
		/// <inheritdoc/>
		public override void SetOffset(FileOffset offset, RVA rva) {
			base.SetOffset(offset, rva);

			uint startOffs = (uint)offset;

			offset += HOT_HEAP_DIR_SIZE;
			rva += HOT_HEAP_DIR_SIZE;
			foreach (var header in headers) {
				if (header == null)
					continue;
				header.SetOffset(offset, rva);
				uint len = header.GetFileLength();
				offset += len;
				rva += len;
				Align(ref offset, ref rva);
			}

			foreach (var hotPool in hotPools) {
				Align(ref offset, ref rva);
				hotPool.SetOffset(offset, rva);
				uint len = hotPool.GetFileLength();
				offset += len;
				rva += len;
			}

			Align(ref offset, ref rva);
			offset += hotPools.Count * 8;
			rva += (uint)hotPools.Count * 8;

			offset += 8;
			rva += 8;

			totalLength = (uint)offset - startOffs;
		}
		/// <summary>
		/// Creates a stream that can access all data starting from <paramref name="offset"/>
		/// </summary>
		/// <param name="self">this</param>
		/// <param name="offset">Offset relative to the beginning of the stream</param>
		/// <returns>A new stream</returns>
		public static IImageStream Create(this IImageStream self, FileOffset offset) {
			return self.Create(offset, long.MaxValue);
		}
Beispiel #41
0
 /// <summary>
 /// Align up
 /// </summary>
 /// <param name="offset">this</param>
 /// <param name="alignment">Alignment</param>
 public static FileOffset AlignUp(this FileOffset offset, uint alignment)
 {
     return((FileOffset)(((uint)offset + alignment - 1) & ~(alignment - 1)));
 }
		/// <summary>
		/// Writes all chunks to <paramref name="writer"/>
		/// </summary>
		/// <param name="writer">The writer</param>
		/// <param name="chunks">All chunks</param>
		/// <param name="offset">File offset of first chunk</param>
		/// <param name="fileAlignment">File alignment</param>
		protected void WriteChunks(BinaryWriter writer, List<IChunk> chunks, FileOffset offset, uint fileAlignment) {
			foreach (var chunk in chunks) {
				chunk.VerifyWriteTo(writer);
				offset += chunk.GetFileLength();
				var newOffset = offset.AlignUp(fileAlignment);
				writer.WriteZeros((int)(newOffset - offset));
				offset = newOffset;
			}
		}
Beispiel #43
0
        void ReadInternal(IImageStream stream)
        {
            stream.Position = 0;
            string sig = Encoding.ASCII.GetString(stream.ReadBytes(30));

            if (sig != "Microsoft C/C++ MSF 7.00\r\n\u001ADS\0")
            {
                throw new PdbException("Invalid signature");
            }
            stream.Position += 2;

            uint pageSize = stream.ReadUInt32();

            /*uint fpm = */ stream.ReadUInt32();
            uint pageCount = stream.ReadUInt32();
            uint rootSize  = stream.ReadUInt32();

            stream.ReadUInt32();
            var numOfRootPages = RoundUpDiv(rootSize, pageSize);
            var numOfPtrPages  = RoundUpDiv(numOfRootPages * 4, pageSize);

            if (pageCount * pageSize != stream.Length)
            {
                throw new PdbException("File size mismatch");
            }

            var pages = new IImageStream[pageCount];

            try {
                FileOffset offset = 0;
                for (uint i = 0; i < pageCount; i++)
                {
                    pages[i] = stream.Create(offset, pageSize);
                    offset  += pageSize;
                }

                var rootPages = new IImageStream[numOfRootPages];
                int pageIndex = 0;
                for (int i = 0; i < numOfPtrPages && pageIndex < numOfRootPages; i++)
                {
                    var ptrPage = pages[stream.ReadUInt32()];
                    ptrPage.Position = 0;
                    for (; ptrPage.Position < ptrPage.Length && pageIndex < numOfRootPages; pageIndex++)
                    {
                        rootPages[pageIndex] = pages[ptrPage.ReadUInt32()];
                    }
                }

                ReadRootDirectory(new MsfStream(rootPages, rootSize), pages, pageSize);
            }
            finally {
                foreach (var page in pages)
                {
                    if (page != null)
                    {
                        page.Dispose();
                    }
                }
            }

            ReadNames();
            ReadStringTable();
            var tokenMapStream = ReadModules();

            documents = new Dictionary <string, DbiDocument>(StringComparer.OrdinalIgnoreCase);
            foreach (var module in modules)
            {
                if (IsValidStreamIndex(module.StreamId))
                {
                    module.LoadFunctions(this, streams[module.StreamId].Content);
                }
            }

            if (IsValidStreamIndex(tokenMapStream ?? STREAM_INVALID_INDEX))
            {
                ApplyRidMap(streams[tokenMapStream.Value].Content);
            }

            functions = new Dictionary <int, DbiFunction>();
            foreach (var module in modules)
            {
                foreach (var func in module.Functions)
                {
                    func.reader = this;
                    functions.Add(func.Token, func);
                }
            }
        }