Пример #1
0
        private void DetectSectionsRamType(MemoryDescriptor mcu = null)
        {
            sectionMemoryTable = new Dictionary <ElfSection, string>();
            var allocSections = new List <ElfSection>();

            //get alloc allocSections
            foreach (var section in DwarfData.File.Sections)
            {
                if ((section.Header.flags & Elf32SectionFlags.SHF_ALLOC) == 0)
                {
                    sectionMemoryTable[section] = unknownMemoryName;
                }
                else
                {
                    allocSections.Add(section);
                }
            }

            if (mcu == null)
            {
                DetectSectionsRamTypeAuto(allocSections);
            }
            else
            {
                DetectSectionsRamTypeByMcu(allocSections, mcu);
            }
            DetectMemoryTypesEx();
        }
Пример #2
0
        public bool IsSupportedFormat()
        {
            bool rv = false;

            if (!File.Exists(DumpFile))
            {
                return(rv);
            }

            using (var dstream = File.OpenRead(DumpFile))
            {
                using (var dbin = new BinaryReader(dstream))
                {
                    // start with a easy to handle format of DMP
                    if (ASCIIEncoding.ASCII.GetString(dbin.ReadBytes(8)) != "PAGEDU64")
                    {
                        return(rv);
                    }

                    dbin.BaseStream.Position = 0x2020;
                    var StartOfMem = dbin.ReadUInt32();

                    // Find the RUN info
                    dbin.BaseStream.Position = 0x88;

                    var MemRunDescriptor = new MemoryDescriptor();
                    MemRunDescriptor.StartOfMemmory = StartOfMem;
                    MemRunDescriptor.NumberOfRuns   = dbin.ReadInt64();
                    MemRunDescriptor.NumberOfPages  = dbin.ReadInt64();

                    // this struct has to fit in the header which is only 0x2000 in total size
                    if (MemRunDescriptor.NumberOfRuns > 32 || MemRunDescriptor.NumberOfRuns < 0)
                    {
                        // TODO: in this case we have to de-patchguard the KDDEBUGGER_DATA block
                    }
                    else
                    {
                        // in this case StartOfMem is 0x2000
                        MemRunDescriptor.StartOfMemmory = 0x2000;

                        rv = true;
                        // we have an embedded RUN in the DMP file that appears to conform to the rules we know
                        for (int i = 0; i < MemRunDescriptor.NumberOfRuns; i++)
                        {
                            var basePage  = dbin.ReadInt64();
                            var pageCount = dbin.ReadInt64();

                            MemRunDescriptor.Run.Add(new MemoryRun()
                            {
                                BasePage = basePage, PageCount = pageCount
                            });
                        }

                        PhysMemDesc = MemRunDescriptor;
                    }
                }
            }
            return(rv);
        }
Пример #3
0
        public BasicRunDetector(string MemSourceFile)
        {
            MemFile = MemSourceFile;

            FileInfo fi = new FileInfo(MemFile);
            SupportedStatus = fi.Exists;

            PhysMemDesc = new MemoryDescriptor(fi.Length);
        }
Пример #4
0
        public BasicRunDetector(string MemSourceFile)
        {
            MemFile = MemSourceFile;

            FileInfo fi = new FileInfo(MemFile);

            SupportedStatus = fi.Exists;

            PhysMemDesc = new MemoryDescriptor(fi.Length);
        }
Пример #5
0
 private void _read()
 {
     _threadId      = m_io.ReadU4le();
     _suspendCount  = m_io.ReadU4le();
     _priorityClass = m_io.ReadU4le();
     _priority      = m_io.ReadU4le();
     _teb           = m_io.ReadU8le();
     _stack         = new MemoryDescriptor(m_io, this, m_root);
     _threadContext = new LocationDescriptor(m_io, this, m_root);
 }
Пример #6
0
        public bool IsSupportedFormat()
        {
            bool rv = false;
            if (!File.Exists(DumpFile))
                return rv;

            using(var dstream = File.OpenRead(DumpFile))
            {
                using (var dbin = new BinaryReader(dstream))
                {
                    // start with a easy to handle format of DMP
                    if (ASCIIEncoding.ASCII.GetString(dbin.ReadBytes(8)) != "PAGEDU64")
                        return rv;

                    dbin.BaseStream.Position = 0x2020;
                    var StartOfMem = dbin.ReadUInt32();

                    // Find the RUN info
                    dbin.BaseStream.Position = 0x88;

                    var MemRunDescriptor = new MemoryDescriptor();
                    MemRunDescriptor.StartOfMemmory = StartOfMem;
                    MemRunDescriptor.NumberOfRuns = dbin.ReadInt64();
                    MemRunDescriptor.NumberOfPages = dbin.ReadInt64();

                    // this struct has to fit in the header which is only 0x2000 in total size
                    if (MemRunDescriptor.NumberOfRuns > 32 || MemRunDescriptor.NumberOfRuns < 0)
                    {
                        // TODO: in this case we have to de-patchguard the KDDEBUGGER_DATA block
                    }
                    else
                    {
                        // in this case StartOfMem is 0x2000
                        MemRunDescriptor.StartOfMemmory = 0x2000;

                        rv = true;
                        // we have an embedded RUN in the DMP file that appears to conform to the rules we know
                        for (int i = 0; i < MemRunDescriptor.NumberOfRuns; i++)
                        {
                            var basePage = dbin.ReadInt64();
                            var pageCount = dbin.ReadInt64();

                            MemRunDescriptor.Run.Add(new MemoryRun() { BasePage = basePage, PageCount = pageCount });
                        }

                        PhysMemDesc = MemRunDescriptor;
                    } 

                }
            }
            return rv;
        }
Пример #7
0
        public MemoryProfile(DwarfData dwData, MemoryDescriptor memoryDescriptor = null)
        {
            DwarfData = dwData;
            DetectSectionsRamType(memoryDescriptor);

            //build memory usage table
            memoryUsageTable = new Dictionary <string, MemoryUsage>();
            var memories = GetMemoryNames();

            if (memories != null)
            {
                foreach (var memory in memories)
                {
                    var sections = GetSectionsByMemoryEx(memory);
                    var mem      = new MemoryUsage {
                        Sections = sections
                    };
                    if (sections != null && sections.Length != 0)
                    {
                        mem.BytesUsed = sections.Aggregate(0UL, (current, section) => current + section.Header.size);

                        if (memoryDescriptor != null && memoryDescriptor.IsEntryExists(memory))
                        {
                            var entry = memoryDescriptor.GetEntryByName(memory);
                            mem.Base   = (ulong)entry.Origin;
                            mem.Length = (ulong)entry.Length;
                        }
                        else
                        {
                        }
                    }


                    memoryUsageTable[memory] = mem;
                }
            }
        }
Пример #8
0
        IntPtr INativeMemoryProvider.AllocateBytes(long numberOfBytes)
        {
            var cashed = _free.Find(md => md.NumberOfBytes == numberOfBytes);

            if (cashed != null)
            {
                _free.Remove(cashed);
                _logger?.WriteStatus($"\t\t\t\tReUsing {numberOfBytes}");
                return(cashed.Ptr);
            }

            var ptr        = AllocateMemory(numberOfBytes);
            var descriptor = new MemoryDescriptor(ptr, numberOfBytes);

            _allocated.Add(descriptor);

            var stack = MemoryUtils.ParseStackTrace();

            var gigaBytes = numberOfBytes / (1024.0 * 1024 * 1024);

            _logger?.WriteError($"Allocating {gigaBytes:######0.0000} GiB ({numberOfBytes} bytes), ptr:{ptr} at {stack[7]}");

            return(ptr);
        }
Пример #9
0
        /// <summary>
        /// This pulls info from the hypervisor areas regarding memory extents
        /// </summary>
        /// <param name="vtero"></param>
        /// <returns></returns>
        public override bool IsSupportedFormat(Vtero vtero)
        {
            long InfoCnt;
            long nr_vcpu, nr_pages = 0, page_size = 0, pfn_LAST, pfn_VAL;

            // use abstract implementation & scan for internal 
            LogicalPhysMemDesc = ExtractMemDesc(vtero);

            if (Elf == null)
                return false;

            using (var dstream = File.OpenRead(vtero.MemFile))
            {
                using (var ebin = new BinaryReader(dstream))
                {
                    ELFInfo = Elf.GetSection(".note.Xen"); // get note stuff and fill in da info 
                    if (ELFInfo != null)
                    {
                        ebin.BaseStream.Position = ELFInfo.Offset;
                        InfoCnt = ebin.ReadInt64();
                        for (long l = 0; l < InfoCnt; l++)
                        {
                            var InfoType = ebin.ReadInt32();
                            ebin.BaseStream.Position += 12;

                            switch (InfoType)
                            {
                                // header type
                                case 0x2000001:
                                    nr_vcpu = ebin.ReadInt64();
                                    nr_pages = ebin.ReadInt64();
                                    page_size = ebin.ReadInt64();
                                    break;
                                // none type
                                case 0x2:
                                    break;
                                default:
                                    break;
                            }

                        }

                        ELFPfn = Elf.GetSection(".xen_pfn");
                        ebin.BaseStream.Position = ELFPfn.Offset;

                        // base page, length
                        
                        long CurrBasePage = 0;
                        long CurrRunLen = 0;
                        // parse the array
                        pfn_LAST = ebin.ReadInt64();
                        for (long pfnx = 0; pfnx < nr_pages; pfnx++)
                        {
                            CurrRunLen++;

                            pfn_VAL = ebin.ReadInt64();
                            if (pfn_LAST + 1 == pfn_VAL)
                            {
                                pfn_LAST = pfn_VAL;
                                continue;
                            }
                            // add run
                            DetectedRuns.Add(CurrBasePage, CurrRunLen);

                            // reset counter
                            // that is adjusted in the value 
                            pfn_LAST = CurrBasePage = pfn_VAL;
                            CurrRunLen = 0;

                            if (CurrBasePage >= nr_pages)
                                break;
                        }
                    }
                }
            }
            ELFPages = Elf.GetSection(".xen_pages");
            if (ELFPages != null)
                StartOfMem = ELFPages.Offset;

            PhysMemDesc = new MemoryDescriptor(nr_pages * page_size);
            PhysMemDesc.NumberOfRuns = DetectedRuns.Count;
            PhysMemDesc.NumberOfPages = nr_pages;
            PhysMemDesc.StartOfMemmory = StartOfMem;
            PhysMemDesc.Run = new List<MemoryRun>();

            foreach (var kvp in DetectedRuns)
                PhysMemDesc.Run.Add(new MemoryRun() { BasePage = kvp.Key, PageCount = kvp.Value });

            return SupportedStatus;
        }
Пример #10
0
        /// <summary>
        /// OK need to double check later but even though there are 64 bits available in the field
        /// only 32bits are seemingly being used.  Otherwise the values have to be interpreted as
        /// physical addresses and not page numbers.
        /// </summary>
        /// <returns></returns>
        public override bool IsSupportedFormat(Vtero vtero)
        {
            // use abstract implementation & scan for internal
            // were actually not going to use this in VMWare since were so good at vmss
            // this is sort of meaningless :(
            //LogicalPhysMemDesc = ExtractMemDesc(vtero);

            bool rv = false;

            if (!File.Exists(vDeviceFile) || !File.Exists(MemFile))
            {
                return(rv);
            }

            // Let's seee how far we can get w/o being to aggressive here
            //using (var dstream = File.OpenRead(vDeviceFile))
            //{
            //    using (var dbin = new BinaryReader(dstream))
            //    {
            //        // D2BE is really easy to extract data from
            //        if (dbin.ReadUInt32() != 0xBED2BED2)
            //            return rv;
            //    }
            //}

            rv = true;

            var MemRunDescriptor = new MemoryDescriptor();

            // vmem files are contagious starting from 0
            MemRunDescriptor.StartOfMemmory = 0;

            var inFile = File.OpenRead(vDeviceFile);

            // TODO: make this (parsing) more precise for additional versions
            var stateData = new byte[0x40000];

            inFile.Read(stateData, 0, stateData.Length);

            var ToFind = ASCIIEncoding.ASCII.GetBytes("regionsCount");
            var rpn    = ASCIIEncoding.ASCII.GetBytes("regionPageNum");
            var ppn    = ASCIIEncoding.ASCII.GetBytes("regionPPN");
            var rsiz   = ASCIIEncoding.ASCII.GetBytes("regionSize");

            int  i;
            bool Found = false;

            for (i = 0; i < stateData.Length - ToFind.Length; i++)
            {
                int n = 0;
                do
                {
                    if (stateData[i + n] != ToFind[n])
                    {
                        break;
                    }

                    n++;
                    if (n >= ToFind.Length)
                    {
                        Found = true;
                    }
                } while (!Found);

                if (Found)
                {
                    break;
                }
            }

            long TotalPages = 0;

            i += ToFind.Length;
            var Count = BitConverter.ToUInt32(stateData, i);

            MemRunDescriptor.NumberOfRuns = Count;
            i += 4; i += 2; // 2 bytes looks like a typeID or some sort of magic
            // below the >> 20 is/was what seemed to be an adjustment for 64-44 bits of
            // physical address range
            // however the additional >> 12 is physical address into physical pages
            // but it seemingly was supposed to be pages to begin with so who knows, but this works
            // maybe it is pages and I needed +4 on the index and then everything works with a .ToUInt32
            // but that now seems short of the physical limits, anyhow, this works ;)
            for (int r = 0; r < Count; r++)
            {
                i += rpn.Length;
                var basePage = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += ppn.Length;
                var ppnVal = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += rsiz.Length;
                var regionSize = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;

                TotalPages += regionSize;

                MemRunDescriptor.Run.Add(new MemoryRun()
                {
                    BasePage = ppnVal, PageCount = regionSize, regionPPN = basePage
                });
            }

            MemRunDescriptor.NumberOfPages = TotalPages;
            PhysMemDesc = MemRunDescriptor;
            // adjust start of memory to
            if (vDeviceFile == MemFile)
            {
                var x = (int)(Math.Ceiling((decimal)i / 0x10000) * 0x10000);
                StartOfMem = x;
            }

            if (TotalPages == 0)
            {
                MemRunDescriptor.NumberOfPages = new FileInfo(MemFile).Length >> MagicNumbers.PAGE_SHIFT;
                PhysMemDesc        = MemRunDescriptor;
                LogicalPhysMemDesc = ExtractMemDesc(vtero);
            }
            return(rv);
        }
Пример #11
0
        /// <summary>
        /// OK need to double check later but even though there are 64 bits available in the field
        /// only 32bits are seemingly being used.  Otherwise the values have to be interpreted as
        /// physical addresses and not page numbers.
        /// </summary>
        /// <returns></returns>
        public override bool IsSupportedFormat(Vtero vtero)
        {
            // use abstract implementation & scan for internal 
            // were actually not going to use this in VMWare since were so good at vmss
            // this is sort of meaningless :( 
            //LogicalPhysMemDesc = ExtractMemDesc(vtero);

            bool rv = false;
            if (!File.Exists(vDeviceFile) || !File.Exists(MemFile))
                return rv;

            using (var dstream = File.OpenRead(vDeviceFile))
            {
                using (var dbin = new BinaryReader(dstream))
                {
                    // D2BE is really easy to extract data from
                    if (dbin.ReadUInt32() != 0xBED2BED2)
                        return rv;
                }
            }

            rv = true;

            var MemRunDescriptor = new MemoryDescriptor();
            // vmem files are contagious starting from 0
            MemRunDescriptor.StartOfMemmory = 0;
            
            var stateData = File.ReadAllBytes(vDeviceFile);
            var ToFind = ASCIIEncoding.ASCII.GetBytes("regionsCount");
            var rpn = ASCIIEncoding.ASCII.GetBytes("regionPageNum");
            var ppn = ASCIIEncoding.ASCII.GetBytes("regionPPN");
            var rsiz = ASCIIEncoding.ASCII.GetBytes("regionSize");

            int i;
            for(i=0; i < stateData.Length-ToFind.Length; i++)
            {
                int n = 0;
                bool Found = false;
                do
                {
                    if (stateData[i + n] != ToFind[n])
                        break;

                    n++;
                    if (n >= ToFind.Length)
                        Found = true;
                } while (!Found);

                if (Found)
                    break;
            }

            long TotalPages = 0;

            i += ToFind.Length;
            var Count = BitConverter.ToUInt32(stateData, i);
            MemRunDescriptor.NumberOfRuns = Count;
            i += 4; i += 2; // 2 bytes looks like a typeID or some sort of magic
            // below the >> 20 is/was what seemed to be an adjustment for 64-44 bits of
            // physical address range
            // however the additional >> 12 is physical address into physical pages
            // but it seemingly was supposed to be pages to begin with so who knows, but this works
            // maybe it is pages and I needed +4 on the index and then everything works with a .ToUInt32
            // but that now seems short of the physical limits, anyhow, this works ;)
            for (int r = 0; r < Count; r++)
            {
                i += rpn.Length;
                var basePage = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += ppn.Length;
                var ppnVal = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += rsiz.Length;
                var regionSize = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;

                TotalPages += regionSize;

                MemRunDescriptor.Run.Add(new MemoryRun() { BasePage = ppnVal, PageCount = regionSize, regionPPN = basePage });
            }

            MemRunDescriptor.NumberOfPages = TotalPages;
            PhysMemDesc = MemRunDescriptor;

            return rv;
        }
Пример #12
0
        /// <summary>
        /// Extract memory extents info from the guest memory
        /// </summary>
        /// <param name="vtero"></param>
        /// <returns></returns>
        public MemoryDescriptor ExtractMemDesc(Vtero vtero)
        {
            MemoryDescriptor MemRunDescriptor = null;
            // rarely used pool tag
            var off = Scanner.BackwardsValueScan(vtero.MemFile, 0x6c4d6d4d);

            using (var dstream = File.OpenRead(vtero.MemFile))
            {
                var  MemSize    = dstream.Length;
                long totPageCnt = 0;

                using (var dbin = new BinaryReader(dstream))
                {
                    foreach (var xoff in off)
                    {
                        //WriteLine($"Checking Memory Descriptor @{(xoff + 28):X}");
                        if (xoff > vtero.FileSize)
                        {
                            //    WriteLine($"offset {xoff:X} > FileSize {vtero.FileSize:X}");
                            continue;
                        }
                        for (long doff = 4; doff <= 64; doff += 4)
                        {
                            dstream.Position = xoff + doff;
                            MemRunDescriptor = new MemoryDescriptor();
                            MemRunDescriptor.NumberOfRuns  = dbin.ReadInt64();
                            MemRunDescriptor.NumberOfPages = dbin.ReadInt64();

                            var RunCnt  = MemRunDescriptor.NumberOfRuns;
                            var PageCnt = MemRunDescriptor.NumberOfPages;

                            //Console.WriteLine($"Runs: {RunCnt}, Pages: {MemRunDescriptor.NumberOfPages} ");
                            long lastBasePage = 0;

                            if (RunCnt > 0 && MemRunDescriptor.NumberOfRuns < 32)
                            {
                                MemRunDescriptor.Run = new List <MemoryRun>((int)RunCnt);
                                for (int i = 0; i < RunCnt; i++)
                                {
                                    var basePage = dbin.ReadInt64();
                                    // error check range too high/low
                                    if (basePage < lastBasePage || basePage < 0)
                                    {
                                        break;
                                    }

                                    lastBasePage = basePage;

                                    var pageCount = dbin.ReadInt64();
                                    if (pageCount > PageCnt || pageCount <= 0)
                                    {
                                        break;
                                    }

                                    totPageCnt += pageCount;
                                    MemRunDescriptor.Run.Add(new MemoryRun()
                                    {
                                        BasePage = basePage, PageCount = pageCount
                                    });
                                }

                                if (totPageCnt > (PageCnt + 1024) || totPageCnt <= 0)
                                {
                                    continue;
                                }

                                // if we have counted more pages than we have in disk
                                // or
                                // if we have less than 1/2 the pages we need (this is fudge factor should be precise right!)
                                if (totPageCnt > (((MemSize - StartOfMem) >> MagicNumbers.PAGE_SHIFT) & 0xffffffff) ||
                                    totPageCnt < (((MemSize - StartOfMem) >> MagicNumbers.PAGE_SHIFT) & 0xffffffff) / 2
                                    )
                                {
                                    //Console.WriteLine($"odd/bad memory run, skipping");
                                    continue;
                                }
                                else
                                {
                                    return(MemRunDescriptor);
                                }
                            }

                            //WriteLine($"MemoryDescriptor {MemRunDescriptor}");
                        }
                    }
                }
            }
#if OLD_CODE
            long aSkipCount = 0;

            for (int i = 0; i < MemRunDescriptor.NumberOfRuns; i++)
            {
                var RunSkip = MemRunDescriptor.Run[i].BasePage - aSkipCount;
                MemRunDescriptor.Run[i].SkipCount = RunSkip;
                aSkipCount = MemRunDescriptor.Run[i].PageCount;
            }
#endif
            //WriteLine("Finished VALUE scan.");
            return(MemRunDescriptor);
        }
Пример #13
0
        /// <summary>
        /// Extract memory extents info from the guest memory
        /// </summary>
        /// <param name="vtero"></param>
        /// <returns></returns>
        public MemoryDescriptor ExtractMemDesc(Vtero vtero)
        {
            MemoryDescriptor MemRunDescriptor = null;
            // rarely used pool tag
            var off = Scanner.BackwardsValueScan(vtero.MemFile, 0x6c4d6d4d);

            using (var dstream = File.OpenRead(vtero.MemFile))
            {
                var MemSize = dstream.Length;
                long totPageCnt = 0;

                using (var dbin = new BinaryReader(dstream))
                {
                    foreach (var xoff in off)
                    {
                        //WriteLine($"Checking Memory Descriptor @{(xoff + 28):X}");
                        if (xoff > vtero.FileSize)
                        {
                            //    WriteLine($"offset {xoff:X} > FileSize {vtero.FileSize:X}");
                            continue;
                        }
                        for (long doff = 4; doff <= 64; doff += 4)
                        {
                            dstream.Position = xoff + doff; 
                            MemRunDescriptor = new MemoryDescriptor();
                            MemRunDescriptor.NumberOfRuns = dbin.ReadInt64();
                            MemRunDescriptor.NumberOfPages = dbin.ReadInt64();

                            var RunCnt = MemRunDescriptor.NumberOfRuns;
                            var PageCnt = MemRunDescriptor.NumberOfPages;

                            //Console.WriteLine($"Runs: {RunCnt}, Pages: {MemRunDescriptor.NumberOfPages} ");
                            long lastBasePage = 0;

                            if (RunCnt > 0 && MemRunDescriptor.NumberOfRuns < 32)
                            {
                                MemRunDescriptor.Run = new List<MemoryRun>((int)RunCnt);
                                for (int i = 0; i < RunCnt; i++)
                                {
                                    var basePage = dbin.ReadInt64();
                                    // error check range too high/low
                                    if (basePage < lastBasePage || basePage < 0)
                                        break;

                                    lastBasePage = basePage;

                                    var pageCount = dbin.ReadInt64();
                                    if (pageCount > PageCnt || pageCount <= 0)
                                        break;

                                    totPageCnt += pageCount;
                                    MemRunDescriptor.Run.Add(new MemoryRun() { BasePage = basePage, PageCount = pageCount });
                                }

                                if (totPageCnt > (PageCnt + 1024) || totPageCnt <= 0)
                                    continue;

                                // if we have counted more pages than we have in disk
                                // or
                                // if we have less than 1/2 the pages we need (this is fudge factor should be precise right!)
                                if (totPageCnt > (((MemSize - StartOfMem) >> MagicNumbers.PAGE_SHIFT) & 0xffffffff) ||
                                    totPageCnt < (((MemSize - StartOfMem) >> MagicNumbers.PAGE_SHIFT) & 0xffffffff) / 2
                                    )
                                {
                                    //Console.WriteLine($"odd/bad memory run, skipping");
                                    continue;
                                }
                                else
                                    return MemRunDescriptor;
                            }

                            //WriteLine($"MemoryDescriptor {MemRunDescriptor}");
                        }
                    }
                }
            }
#if OLD_CODE
            long aSkipCount = 0;

            for (int i=0; i < MemRunDescriptor.NumberOfRuns; i++)
            {
                var RunSkip = MemRunDescriptor.Run[i].BasePage - aSkipCount;
                MemRunDescriptor.Run[i].SkipCount = RunSkip;
                aSkipCount = MemRunDescriptor.Run[i].PageCount;
            }
#endif
            //WriteLine("Finished VALUE scan.");
            return MemRunDescriptor;
        }
Пример #14
0
        static void Main(string[] args)
        {
            //string linkerScriptPath = @"C:/Users/Sergey/AppData/Local/VisualGDB/EmbeddedBSPs/arm-eabi/com.sysprogs.arm.stm32/STM32F4xxxx-HAL/LinkerScripts/STM32F439xI_flash.lds";
            string           elfFilePath = @"D:\MotionParallaxResearch\NMarker\V03\Software\ATmega328P\ATmega328P\ATmega328P\Debug\ATmega328P.elf";
            MemoryDescriptor mem         = null;// MemoryDescriptor.FromLinkerScript(linkerScriptPath);


            ElfFile   elf    = new ElfFile(File.ReadAllBytes(elfFilePath));
            DwarfData dwData = new DwarfData(elf);

            MemoryProfile profile = new MemoryProfile(dwData, mem);

            var flashSections = profile.GetFlashSections();
            var progSections  = profile.GetProgramSections();



            var memNames = profile.GetMemoryNames();

            foreach (var name in memNames)
            {
                var sections = profile.GetSectionsByMemoryEx(name);
                Console.ForegroundColor = ConsoleColor.Red;
                Console.WriteLine("Memory: {0}", name);

                ulong totalSize = 0;
                foreach (var section in sections)
                {
                    Console.ForegroundColor = ConsoleColor.Green;
                    Console.WriteLine("\t{0} : {1}", section.Name, section.Header.size);
                    totalSize += section.Header.size;

                    //print symbols
                    var fileGroups = section.Items.GroupBy(v => Path.GetFileName(v.FileStr)).ToArray();
                    foreach (var fileGroup in fileGroups)
                    {
                        Console.ForegroundColor = ConsoleColor.Blue;
                        Console.WriteLine("\t\t{0} : ", fileGroup.Key);
                        Console.ResetColor();

                        foreach (var item in fileGroup)
                        {
                            var p1 = string.Format("\t\t\t{0}:", item.Name);
                            if (p1.Length < 14)
                            {
                                p1 += "\t";
                            }
                            if (p1.Length < 25)
                            {
                                p1 += "\t";
                            }
                            Console.WriteLine(p1 + string.Format("\t{0}:\t0x{1:x}", item.Size, item.Pc));
                        }
                    }
                }
                Console.WriteLine("\tTotal size: {0}", totalSize);
            }


            var flashSize = flashSections.Aggregate <ElfSection, ulong>(0, (current, item) => current + item.Header.size);

            var prgSize = progSections.Aggregate <ElfSection, ulong>(0, (current, item) => current + item.Header.size);

            Console.ReadLine();
        }
Пример #15
0
 private void DetectSectionsRamTypeByMcu(IEnumerable <ElfSection> allocSections, MemoryDescriptor mcu)
 {
     foreach (var section in allocSections)
     {
         sectionMemoryTable[section] = unknownMemoryName;
         foreach (var memoryEntry in mcu.Entries)
         {
             if ((section.Header.addr >= memoryEntry.Origin) &&
                 (section.Header.addr <= (memoryEntry.Origin + memoryEntry.Length)))
             {
                 sectionMemoryTable[section] = memoryEntry.Name;
                 break;
             }
         }
     }
 }
Пример #16
0
        public override bool IsSupportedFormat(Vtero vtero)
        {
            bool rv = false;

            if (!File.Exists(DumpFile))
            {
                return(rv);
            }

            // use abstract implementation & scan for internal
            LogicalPhysMemDesc = ExtractMemDesc(vtero);

            using (var dstream = File.OpenRead(DumpFile))
            {
                MemSize = dstream.Length;

                using (var dbin = new BinaryReader(dstream))
                {
                    // start with a easy to handle format of DMP
                    if (ASCIIEncoding.ASCII.GetString(dbin.ReadBytes(8)) != "PAGEDU64")
                    {
                        return(rv);
                    }

                    dbin.BaseStream.Position = 0x2020;
                    StartOfMem = dbin.ReadUInt32();

                    // Find the RUN info
                    dbin.BaseStream.Position = 0x88;

                    var MemRunDescriptor = new MemoryDescriptor();
                    MemRunDescriptor.StartOfMemmory = StartOfMem;
                    MemRunDescriptor.NumberOfRuns   = dbin.ReadInt64();
                    MemRunDescriptor.NumberOfPages  = dbin.ReadInt64();

                    // this struct has to fit in the header which is only 0x2000 in total size
                    if (MemRunDescriptor.NumberOfRuns > 32 || MemRunDescriptor.NumberOfRuns < 0)
                    {
                        // TODO: in this case we have to de-patchguard the KDDEBUGGER_DATA block
                        // before resulting to that... implemented a memory scanning mode to extract the runs out via struct detection
                        PhysMemDesc = LogicalPhysMemDesc;
                        PhysMemDesc.StartOfMemmory = StartOfMem;
                        // physmem is preferred place to load from so if we have only 1 run move it to phys.
                        LogicalPhysMemDesc = null;
                    }
                    else
                    {
                        // in this case StartOfMem is 0x2000
                        MemRunDescriptor.StartOfMemmory = 0x2000;

                        // we have an embedded RUN in the DMP file that appears to conform to the rules we know
                        for (int i = 0; i < MemRunDescriptor.NumberOfRuns; i++)
                        {
                            var basePage  = dbin.ReadInt64();
                            var pageCount = dbin.ReadInt64();

                            MemRunDescriptor.Run.Add(new MemoryRun()
                            {
                                BasePage = basePage, PageCount = pageCount
                            });
                        }
                        PhysMemDesc = MemRunDescriptor;
                    }
                    rv = true;
                }
            }

#if OLD_CODE
            long aSkipCount = 0;

            for (int i = 0; i < PhysMemDesc.NumberOfRuns; i++)
            {
                var RunSkip = PhysMemDesc.Run[i].BasePage - aSkipCount;
                PhysMemDesc.Run[i].SkipCount = RunSkip;
                aSkipCount = PhysMemDesc.Run[i].BasePage + PhysMemDesc.Run[i].PageCount;
            }
#endif
            return(rv);
        }
Пример #17
0
        /// <summary>
        /// OK need to double check later but even though there are 64 bits available in the field
        /// only 32bits are seemingly being used.  Otherwise the values have to be interpreted as
        /// physical addresses and not page numbers.
        /// </summary>
        /// <returns></returns>
        public bool IsSupportedFormat()
        {
            bool rv = false;

            if (!File.Exists(vDeviceFile) || !File.Exists(MemFile))
            {
                return(rv);
            }

            using (var dstream = File.OpenRead(vDeviceFile))
            {
                using (var dbin = new BinaryReader(dstream))
                {
                    // D2BE is really easy to extract data from
                    if (dbin.ReadUInt32() != 0xBED2BED2)
                    {
                        return(rv);
                    }
                }
            }

            rv = true;

            var MemRunDescriptor = new MemoryDescriptor();

            // vmem files are contagious starting from 0
            MemRunDescriptor.StartOfMemmory = 0;

            var stateData = File.ReadAllBytes(vDeviceFile);
            var ToFind    = ASCIIEncoding.ASCII.GetBytes("regionsCount");
            var rpn       = ASCIIEncoding.ASCII.GetBytes("regionPageNum");
            var ppn       = ASCIIEncoding.ASCII.GetBytes("regionPPN");
            var rsiz      = ASCIIEncoding.ASCII.GetBytes("regionSize");

            int i;

            for (i = 0; i < stateData.Length - ToFind.Length; i++)
            {
                int  n     = 0;
                bool Found = false;
                do
                {
                    if (stateData[i + n] != ToFind[n])
                    {
                        break;
                    }

                    n++;
                    if (n >= ToFind.Length)
                    {
                        Found = true;
                    }
                } while (!Found);

                if (Found)
                {
                    Console.WriteLine($"Found it at 0x{i:X}");
                    break;
                }
            }

            long TotalPages = 0;

            i += ToFind.Length;
            var Count = BitConverter.ToUInt32(stateData, i);

            MemRunDescriptor.NumberOfRuns = Count;
            i += 4; i += 2; // 2 bytes looks like a typeID or some sort of magic
            // below the >> 20 is/was what seemed to be an adjustment for 64-44 bits of
            // physical address range
            // however the additional >> 12 is physical address into physical pages
            // but it seemingly was supposed to be pages to begin with so who knows, but this works
            // maybe it is pages and I needed +4 on the index and then everything works with a .ToUInt32
            // but that now seems short of the physical limits, anyhow, this works ;)
            for (int r = 0; r < Count; r++)
            {
                i += rpn.Length;
                var basePage = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += ppn.Length;
                var ppnVal = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;
                i += rsiz.Length;
                var regionSize = BitConverter.ToInt64(stateData, i) >> 20 >> 12;
                i += 8; i += 2;

                TotalPages += (regionSize >> 12);


                MemRunDescriptor.Run.Add(new MemoryRun()
                {
                    BasePage = ppnVal, PageCount = regionSize, regionPPN = basePage
                });
            }

            MemRunDescriptor.NumberOfPages = TotalPages;
            PhysMemDesc = MemRunDescriptor;

            return(rv);
        }
Пример #18
0
        public void Reload(string elfFilePath, string linkerScrintFilePath)
        {
            _elfUri = new Uri(elfFilePath);
            try {
                File = new ElfFile(System.IO.File.ReadAllBytes(elfFilePath));
            }
            catch (Exception ex) {
                Debug.WriteLine(ex.Message);
                return;
            }

            _dwarf = new DwarfData(_elfFile);

            _memoryDescriptor = System.IO.File.Exists(linkerScrintFilePath) ? MemoryDescriptor.FromLinkerScript(linkerScrintFilePath) : null;

            Profile = new MemoryProfile(_dwarf, _memoryDescriptor);
            Symbols.Clear();
            foreach (var memoryName in Profile.MemoryNames)
            {
                var adapter = new MemoryTypeAdapter(Profile, memoryName);
                foreach (var section in adapter.Sections)
                {
                    foreach (var symbol in section.Symbols)
                    {
                        if (symbol.Header.Info.SymbolType == Elf32SymbolType.STT_SECTION)
                        {
                            continue;
                        }
                        SymbolDescriptor desc = new SymbolDescriptor();
                        desc.Section = section;
                        desc.Memory  = adapter;
                        desc.Symbol  = symbol;

                        desc.DwarfUnitItem =
                            _dwarf.globalItems.FirstOrDefault(v => v.Name == symbol.Name);

                        /*Uri address1 = new Uri("http://www.contoso.com/");
                         *
                         * // Create a new Uri from a string.
                         * Uri address2 = new Uri("http://www.contoso.com/index.htm?date=today");
                         *
                         * // Determine the relative Uri.
                         * Console.WriteLine("The difference is {0}", address1.MakeRelativeUri(address2));*/

                        if (!string.IsNullOrEmpty(desc.DwarfUnitItem?.FileStr))
                        {
                            if (System.IO.File.Exists(desc.DwarfUnitItem.FileStr))
                            {
                                Uri elfUri       = new Uri(elfFilePath);
                                Uri symbolUri    = new Uri(desc.DwarfUnitItem.FileStr);
                                Uri relativePath = elfUri.MakeRelativeUri(symbolUri);
                                desc.DwarfUnitItem.FileStr = relativePath.ToString();
                            }
                        }

                        Symbols.Add(desc);
                    }
                }
            }
            UpdateTitle();
        }
Пример #19
0
        /// <summary>
        /// This pulls info from the hypervisor areas regarding memory extents
        /// </summary>
        /// <param name="vtero"></param>
        /// <returns></returns>
        public override bool IsSupportedFormat(Vtero vtero)
        {
            long InfoCnt;
            long nr_vcpu, nr_pages = 0, page_size = 0, pfn_LAST, pfn_VAL;

            // use abstract implementation & scan for internal
            LogicalPhysMemDesc = ExtractMemDesc(vtero);

            if (Elf == null)
            {
                return(false);
            }

            using (var dstream = File.OpenRead(vtero.MemFile))
            {
                using (var ebin = new BinaryReader(dstream))
                {
                    ELFInfo = Elf.GetSection(".note.Xen"); // get note stuff and fill in da info
                    if (ELFInfo != null)
                    {
                        ebin.BaseStream.Position = ELFInfo.Offset;
                        InfoCnt = ebin.ReadInt64();
                        for (long l = 0; l < InfoCnt; l++)
                        {
                            var InfoType = ebin.ReadInt32();
                            ebin.BaseStream.Position += 12;

                            switch (InfoType)
                            {
                            // header type
                            case 0x2000001:
                                nr_vcpu   = ebin.ReadInt64();
                                nr_pages  = ebin.ReadInt64();
                                page_size = ebin.ReadInt64();
                                break;

                            // none type
                            case 0x2:
                                break;

                            default:
                                break;
                            }
                        }

                        ELFPfn = Elf.GetSection(".xen_pfn");
                        ebin.BaseStream.Position = ELFPfn.Offset;

                        // base page, length

                        long CurrBasePage = 0;
                        long CurrRunLen   = 0;
                        // parse the array
                        pfn_LAST = ebin.ReadInt64();
                        for (long pfnx = 0; pfnx < nr_pages; pfnx++)
                        {
                            CurrRunLen++;

                            pfn_VAL = ebin.ReadInt64();
                            if (pfn_LAST + 1 == pfn_VAL)
                            {
                                pfn_LAST = pfn_VAL;
                                continue;
                            }
                            // add run
                            DetectedRuns.Add(CurrBasePage, CurrRunLen);

                            // reset counter
                            // that is adjusted in the value
                            pfn_LAST   = CurrBasePage = pfn_VAL;
                            CurrRunLen = 0;

                            if (CurrBasePage >= nr_pages)
                            {
                                break;
                            }
                        }
                    }
                }
            }
            ELFPages = Elf.GetSection(".xen_pages");
            if (ELFPages != null)
            {
                StartOfMem = ELFPages.Offset;
            }

            PhysMemDesc = new MemoryDescriptor(nr_pages * page_size);
            PhysMemDesc.NumberOfRuns   = DetectedRuns.Count;
            PhysMemDesc.NumberOfPages  = nr_pages;
            PhysMemDesc.StartOfMemmory = StartOfMem;
            PhysMemDesc.Run            = new List <MemoryRun>();

            foreach (var kvp in DetectedRuns)
            {
                PhysMemDesc.Run.Add(new MemoryRun()
                {
                    BasePage = kvp.Key, PageCount = kvp.Value
                });
            }

            return(SupportedStatus);
        }
Пример #20
0
        public static Vtero Scanit(ConfigOptions co)
        {
            bool SkipVMCS = (co.VersionsToEnable & PTType.VMCS) != PTType.VMCS;
            var  Filename = co.FileName;

            co.VersionsToEnable = co.VersionsToEnable & ~PTType.VMCS;

            // allocate now so that we can un-serialize or keep an instance
            Vtero vtero = new Vtero();

            // this instance is temporally used for loading state
            // i.e. don't set properties or fields here
            if (!co.IgnoreSaveData)
            {
                vtero = vtero.CheckpointRestoreState(Filename);
                if (vtero == null)
                {
                    vtero = new Vtero();
                }
                else
                {
                    vtero.OverRidePhase = true;
                }
            }

            if (vtero.Phase < 2)
            {
                if (!co.ForceSingleFlatMemRun)
                {
                    vtero = new Vtero(Filename);
                }
                else
                {
                    var siz = new FileInfo(co.FileName).Length;
                    vtero.MRD             = new BasicRunDetector();
                    vtero.MRD.MemFile     = co.FileName;
                    vtero.MRD.vDeviceFile = co.FileName;
                    vtero.MRD.PhysMemDesc = new MemoryDescriptor(siz);
                    vtero = new Vtero(Filename, vtero.MRD);
                }
            }

            if (!vtero.OverRidePhase)
            {
                Mem.InitMem(co.FileName, vtero.MRD);
                //ProgressBarz.BaseMessage = new ConsoleString("First pass, looking for processes");
                ForegroundColor = ConsoleColor.Cyan;
#if TESTING
                Timer = Stopwatch.StartNew();

                if ((Version & PTType.VALUE) == PTType.VALUE)
                {
                    var off = vtero.ScanValue(Is64Scan, valuL, 0);

                    WriteLine(FormatRate(vtero.FileSize, Timer.Elapsed));
                    using (var dstream = File.OpenRead(vtero.MemFile))
                    {
                        using (var dbin = new BinaryReader(dstream))
                        {
                            foreach (var xoff in off)
                            {
                                WriteLine($"Checking Memory Descriptor @{(xoff + 28):X}");
                                if (xoff > vtero.FileSize)
                                {
                                    WriteLine($"offset {xoff:X} > FileSize {vtero.FileSize:X}");
                                    continue;
                                }

                                dstream.Position = xoff + 28;
                                var MemRunDescriptor = new MemoryDescriptor();
                                MemRunDescriptor.NumberOfRuns  = dbin.ReadInt64();
                                MemRunDescriptor.NumberOfPages = dbin.ReadInt64();

                                Console.WriteLine($"Runs: {MemRunDescriptor.NumberOfRuns}, Pages: {MemRunDescriptor.NumberOfPages} ");

                                if (MemRunDescriptor.NumberOfRuns < 0 || MemRunDescriptor.NumberOfRuns > 32)
                                {
                                    continue;
                                }
                                for (int i = 0; i < MemRunDescriptor.NumberOfRuns; i++)
                                {
                                    var basePage  = dbin.ReadInt64();
                                    var pageCount = dbin.ReadInt64();

                                    MemRunDescriptor.Run.Add(new MemoryRun()
                                    {
                                        BasePage = basePage, PageCount = pageCount
                                    });
                                }
                                WriteLine($"MemoryDescriptor {MemRunDescriptor}");
                            }
                        }
                    }
                    WriteLine("Finished VALUE scan.");
                    return;
                }
                if ((Version & PTType.VALUE) == PTType.VALUE)
                {
                    return;
                }
#endif
            }
            // basic perf checking
            //QuickOptions.Timer = Stopwatch.StartNew();

            var procCount = vtero.ProcDetectScan(co.VersionsToEnable);

            // second pass
            // with the page tables we acquired, locate candidate VMCS pages in the format
            // [31-bit revision id][abort indicator]
            // the page must also have at least 1 64bit value which is all set (-1)
            // Root-HOST CR3 will have uniform diff
            // unless an extent based dump image is input, some .DMP variations
            // TODO: Add support for extent based inputs
            // Guest VMCS will contain host CR3 & guest CR3 (hCR3 & gCR3)
            // sometimes CR3 will be found in multiple page tables, e.g. system process or SMP
            // if I have more than 1 CR3 from different file_offset, just trim them out for now
            // future may have a reason to isolate based on original locationAG

            if (SkipVMCS)
            {
                if (!vtero.OverRidePhase)
                {
                    vtero.GroupAS();
                }

                if (co.VerboseLevel > 1)
                {
                    WriteColor(ConsoleColor.Yellow, "Skipping VMCS scan (as requested).");
                }
            }
            else
            {
                //ProgressBarz.BaseMessage = new ConsoleString("Second pass, correlating for VMCS pages");

                var VMCSCount = vtero.VMCSScan();
                //Timer.Stop();

                if (!vtero.OverRidePhase)
                {
                    //WriteColor(ConsoleColor.Blue, ConsoleColor.Yellow, $"{VMCSCount} candidate VMCS pages. Time to process: {QuickOptions.Timer.Elapsed}, Data scanned: {vtero.FileSize:N}");

                    // second time
                    //WriteColor(ConsoleColor.Blue, ConsoleColor.Yellow, $"Second pass done. {QuickOptions.FormatRate(vtero.FileSize * 2, QuickOptions.Timer.Elapsed)}");

                    // each of these depends on a VMCS scan/pass having been done at the moment
                    WriteColor(ConsoleColor.Cyan, ConsoleColor.Black, "grouping and joining all memory");
                }
                // After this point were fairly functional
                vtero.GroupAS();
            }
            // sync-save state so restarting is faster
            if (!co.IgnoreSaveData)
            {
                if (Vtero.VerboseLevel > 0)
                {
                    Write($"Saving checkpoint... ");
                }

                var saveStateFile = vtero.CheckpointSaveState();
                WriteColor(ConsoleColor.White, saveStateFile);
            }
            Console.CursorVisible = true;
            return(vtero);
        }