Ejemplo n.º 1
0
        public Minidump(string crashDump)
        {
            if (!File.Exists(crashDump))
            {
                throw new FileNotFoundException(crashDump);
            }

            _crashDump = crashDump;
            FileStream stream = File.Open(crashDump, FileMode.Open, FileAccess.Read, FileShare.Read);

            // Load header
            MinidumpHeader header = Read <MinidumpHeader>(stream);

            if (!header.IsValid)
            {
                throw new InvalidDataException($"File '{crashDump}' is not a Minidump.");
            }

            _directories = new MinidumpDirectory[header.NumberOfStreams];

            stream.Position = header.StreamDirectoryRva;
            if (!Read(stream, _directories))
            {
                throw new InvalidDataException($"Unable to read directories from minidump '{crashDump} offset 0x{header.StreamDirectoryRva:x}");
            }

            (int systemInfoIndex, int moduleListIndex) = FindImportantStreams(crashDump);

            // Architecture is the first entry in MINIDUMP_SYSTEM_INFO.  We need nothing else out of that struct,
            // so we only read the first entry.
            // https://docs.microsoft.com/en-us/windows/win32/api/minidumpapiset/ns-minidumpapiset-minidump_system_info
            Architecture = Read <MinidumpProcessorArchitecture>(stream, _directories[systemInfoIndex].Rva);

            // Initialize modules.  DataTarget will need a module list immediately, so there's no reason to delay
            // filling in the module list.
            long rva   = _directories[moduleListIndex].Rva;
            uint count = Read <uint>(stream, rva);

            rva += sizeof(uint);
            MinidumpModule[] modules = new MinidumpModule[count];

            if (Read(stream, rva, modules))
            {
                Modules = modules.AsImmutableArray();
            }
            else
            {
                Modules = ImmutableArray <MinidumpModule> .Empty;
            }

            // Read segments async.
            _memoryTask = GetMemoryReader();
            _threadTask = ReadThreadData(stream);
        }
Ejemplo n.º 2
0
        public Minidump(string crashDump, FileStream stream, CacheOptions cacheOptions)
        {
            if (!File.Exists(crashDump))
            {
                throw new FileNotFoundException(crashDump);
            }

            _crashDump = crashDump;

            // Load header
            MinidumpHeader header = Read <MinidumpHeader>(stream);

            if (!header.IsValid)
            {
                throw new InvalidDataException($"File '{crashDump}' is not a Minidump.");
            }

            _directories = new MinidumpDirectory[header.NumberOfStreams];

            stream.Position = header.StreamDirectoryRva;
            if (!Read(stream, _directories))
            {
                throw new InvalidDataException($"Unable to read directories from minidump '{crashDump} offset 0x{header.StreamDirectoryRva:x}");
            }

            (int systemInfoIndex, int moduleListIndex) = FindImportantStreams(crashDump);

            // Architecture is the first entry in MINIDUMP_SYSTEM_INFO.  We need nothing else out of that struct,
            // so we only read the first entry.
            // https://docs.microsoft.com/en-us/windows/win32/api/minidumpapiset/ns-minidumpapiset-minidump_system_info
            Architecture = Read <MinidumpProcessorArchitecture>(stream, _directories[systemInfoIndex].Rva);

            // Initialize modules.  DataTarget will need a module list immediately, so there's no reason to delay
            // filling in the module list.
            long rva   = _directories[moduleListIndex].Rva;
            uint count = Read <uint>(stream, rva);

            rva += sizeof(uint);
            MinidumpModule[] modules = new MinidumpModule[count];

            if (Read(stream, rva, modules))
            {
                Modules = modules.AsImmutableArray();
            }
            else
            {
                Modules = ImmutableArray <MinidumpModule> .Empty;
            }

            // Read segments async.
            //_nativeMemory = new CachedMemoryReader(pointerSize, dumpPath, cacheSize, CacheTechnology.ArrayPool, _segments.ToImmutableArray());
            ImmutableArray <MinidumpSegment> segments = GetSegments(stream);

            int cacheSize = cacheOptions.MaxDumpCacheSize > int.MaxValue ? int.MaxValue : (int)cacheOptions.MaxDumpCacheSize;

            bool isTinyDump = new FileInfo(crashDump).Length <= cacheSize;

            if (isTinyDump)
            {
                _file = MemoryMappedFile.CreateFromFile(stream, null, 0, MemoryMappedFileAccess.Read, HandleInheritability.None, leaveOpen: false);
                MemoryMappedViewStream mmStream = _file.CreateViewStream(0, 0, MemoryMappedFileAccess.Read);
                MemoryReader = new UncachedMemoryReader(segments, mmStream, PointerSize);
            }
            else if (cacheSize < CachedMemoryReader.MinimumCacheSize)
            {
                // this will be very slow
                MemoryReader = new UncachedMemoryReader(segments, stream, PointerSize);
            }
            else
            {
                CacheTechnology technology = cacheOptions.UseOSMemoryFeatures ? CacheTechnology.AWE : CacheTechnology.ArrayPool;
                MemoryReader = new CachedMemoryReader(segments, crashDump, stream, cacheSize, technology, PointerSize);
            }

            _threadTask = ReadThreadData(stream);
        }