Пример #1
0
        public void uMipsDis_Generate()
        {
            var ab  = new byte[1000];
            var rnd = new Random(0x4711);

            rnd.NextBytes(ab);
            var mem  = new MemoryArea(Address.Ptr32(0x00100000), ab);
            var rdr  = new BeImageReader(mem, 0);
            var dasm = new MicroMipsDisassembler(arch, rdr);

            foreach (var instr in dasm)
            {
            }
        }
Пример #2
0
        public void LoadElfIdentification()
        {
            var rdr      = new BeImageReader(base.RawImage, 0);
            var elfMagic = rdr.ReadBeInt32();

            if (elfMagic != ELF_MAGIC)
            {
                throw new BadImageFormatException("File is not in ELF format.");
            }
            this.fileClass   = rdr.ReadByte();
            this.endianness  = rdr.ReadByte();
            this.fileVersion = rdr.ReadByte();
            this.osAbi       = rdr.ReadByte();
        }
Пример #3
0
        private void Given_Relocator()
        {
            var sc       = new ServiceContainer();
            var arch     = new M68kArchitecture(sc, "m68k", new Dictionary <string, object>());
            var platform = new MacOSClassic(sc, arch)
            {
                A5World  = a5world,
                A5Offset = 2048,
            };
            var mem = (ByteMemoryArea)platform.A5World.MemoryArea;
            var rdr = new BeImageReader(mem, 0);

            this.relocator = new A5Relocator(platform, rdr, 1024);
        }
Пример #4
0
        private void PopulateImports()
        {
            BeImageReader memRdr = new BeImageReader(xexData.memoryData);

            for (int i = 0; i < xexData.import_records.Count; i++)
            {
                UInt32 tableAddress = xexData.import_records[i];

                UInt32 memOffset = tableAddress - xexData.exe_address;
                if (memOffset > xexData.memorySize)
                {
                    throw new BadImageFormatException($"XEX: invalid import record offset: 0x{memOffset}");
                }

                UInt32 value = memRdr.ReadAt <UInt32>(memOffset, rdr => rdr.ReadUInt32());

                byte type     = (byte)((value & 0xFF000000) >> 24);
                byte libIndex = (byte)((value & 0x00FF0000) >> 16);

                if (type == 0)
                {
                    if (libIndex >= xexData.libNames.Count)
                    {
                        throw new BadImageFormatException($"XEX: invalid import type 0 record lib index ({libIndex}, max:{xexData.libNames.Count})");
                    }

                    UInt32 importOrdinal = (value & 0xFFFF);
                    string importLibName = xexData.libNames[libIndex];
                    UInt32 importAddress = xexData.import_records[i];

                    var theAddress = new Address32(importAddress);
                    imports.Add(theAddress, new OrdinalImportReference(theAddress, importLibName, (int)importOrdinal, SymbolType.ExternalProcedure));
                }
                else if (type == 1)
                {
                    if (libIndex >= xexData.libNames.Count)
                    {
                        throw new BadImageFormatException($"XEX: invalid import type 0 record lib index ({libIndex}, max:{xexData.libNames.Count})");
                    }

                    UInt32 importOrdinal = (value & 0xFFFF);
                    string importLibName = xexData.libNames[libIndex];
                    UInt32 importAddress = xexData.import_records[i];

                    var theAddress = new Address32(importAddress);
                    imports.Add(theAddress, new OrdinalImportReference(theAddress, importLibName, (int)importOrdinal, SymbolType.ExternalProcedure));
                }
            }
        }
Пример #5
0
        public override Program Load(Address?addrLoad)
        {
            var rdr = new BeImageReader(RawImage);

            if (!TryLoadHeader(rdr, out var hdr))
            {
                throw new BadImageFormatException();
            }

            addrLoad ??= PreferredBaseAddress;
            var cfgSvc   = Services.RequireService <IConfigurationService>();
            var arch     = cfgSvc.GetArchitecture("m68k") !;
            var env      = cfgSvc.GetEnvironment("atariTOS");
            var platform = env.Load(Services, arch);

            var bytes = new byte[hdr.TextSize + hdr.DataSize + hdr.BssSize];
            var mem   = arch.CreateMemoryArea(addrLoad, bytes);
            int cRead = rdr.ReadBytes(bytes, 0, hdr.TextSize + hdr.DataSize);

            if (cRead != hdr.TextSize + hdr.DataSize)
            {
                throw new BadImageFormatException();
            }

            var text = new ImageSegment(".text", addrLoad, mem, AccessMode.ReadExecute)
            {
                Size = hdr.TextSize
            };
            var data = new ImageSegment(".data", addrLoad + hdr.TextSize, mem, AccessMode.ReadWrite)
            {
                Size = hdr.DataSize
            };
            var bss = new ImageSegment(".bss", addrLoad + hdr.TextSize + hdr.DataSize, mem, AccessMode.ReadWrite)
            {
                Size = hdr.BssSize
            };

            //$TODO: Implement symbols. For now just skip over them.
            rdr.Offset += hdr.SymbolsSize;

            PerformRelocations(mem, rdr);


            var map = new SegmentMap(
                addrLoad,
                text, data, bss);

            return(new Program(map, arch, platform));
        }
Пример #6
0
        private void PopulateImports()
        {
            BeImageReader memRdr = new BeImageReader(xexData.memoryData);

            for (int i = 0; i < xexData.import_records.Count; i++)
            {
                UInt32 tableAddress = xexData.import_records[i];

                UInt32 memOffset = tableAddress - xexData.exe_address;
                if (memOffset > xexData.memorySize)
                {
                    throw new BadImageFormatException($"XEX: invalid import record offset: 0x{memOffset}");
                }

                UInt32 value = memRdr.ReadAt <UInt32>(memOffset, rdr => rdr.ReadUInt32());

                XexImportType type     = (XexImportType)((value & 0xFF000000) >> 24);
                byte          libIndex = (byte)((value & 0x00FF0000) >> 16);

                if (type > XexImportType.Function)
                {
                    decompilerEventListener.Error(
                        $"XEX: Unsupported import type {type}, value: 0x{value:X}");
                    continue;
                }

                if (libIndex >= xexData.libNames.Count)
                {
                    throw new BadImageFormatException($"XEX: invalid import record lib index ({libIndex}, max:{xexData.libNames.Count})");
                }

                UInt32    importOrdinal = (value & 0xFFFF);
                string    importLibName = xexData.libNames[libIndex];
                Address32 importAddress = new Address32(xexData.import_records[i]);

                SymbolType symbolType = SymbolType.Unknown;
                switch (type)
                {
                case XexImportType.Data:
                    symbolType = SymbolType.Data;
                    break;

                case XexImportType.Function:
                    symbolType = SymbolType.ExternalProcedure;
                    break;
                }
                imports.Add(importAddress, new OrdinalImportReference(importAddress, importLibName, (int)importOrdinal, symbolType));
            }
        }
Пример #7
0
        private long PerformanceTest_Simulated(byte[] buf, Decoder root)
        {
            var       rdr  = new BeImageReader(buf);
            var       dasm = new Disassembler(rdr, root);
            Stopwatch sw   = new Stopwatch();

            sw.Start();
            foreach (var instr in dasm)
            {
            }
            sw.Stop();
            var time = sw.ElapsedMilliseconds;

            return(time);
        }
Пример #8
0
        protected override MemoryArea RewriteCode(uint[] words)
        {
            byte[] bytes = words.SelectMany(w => new byte[]
            {
                (byte)(w >> 24),
                (byte)(w >> 16),
                (byte)(w >> 8),
                (byte)w
            }).ToArray();
            var image = new MemoryArea(LoadAddress, bytes);

            this.rdr = image.CreateBeReader(LoadAddress);
            dasm     = mkDasm(rdr);
            return(image);
        }
Пример #9
0
        public override Program Load(Address addrLoad)
        {
            arch = new M68kArchitecture();
            var imgReader = new BeImageReader(RawImage, 0);
            var parse     = new HunkFileParser(imgReader, false);

            this.hunkFile = parse.Parse();
            BuildSegments();
            this.firstCodeHunk = parse.FindFirstCodeHunk();
            var image = new LoadedImage(addrLoad, RelocateBytes(addrLoad));

            return(new Program(
                       image,
                       image.CreateImageMap(),
                       arch,
                       new AmigaOSPlatform(Services, arch)));
        }
Пример #10
0
        public override Program Load(Address?addrLoad)
        {
            BeImageReader rdr = new BeImageReader(this.RawImage, 0);
            FileHeader64? str = rdr.ReadStruct <FileHeader64>();

            if (!str.HasValue)
            {
                throw new BadImageFormatException("Invalid XCoff64 header.");
            }
            var mem      = new ByteMemoryArea(addrLoad ?? PreferredBaseAddress, RawImage);
            var seg      = new ImageSegment("foo", mem, AccessMode.ReadWriteExecute);
            var map      = new SegmentMap(seg);
            var cfgSvc   = Services.RequireService <IConfigurationService>();
            var arch     = cfgSvc.GetArchitecture("ppc-64-be") !;
            var platform = new DefaultPlatform(Services, arch);

            return(new Program(map, arch, platform));
        }
Пример #11
0
        public override Program Load(Address addrLoad)
        {
            var cfgSvc = Services.RequireService <IConfigurationService>();

            arch = (M68kArchitecture)cfgSvc.GetArchitecture("m68k");
            var imgReader = new BeImageReader(RawImage, 0);
            var parse     = new HunkFileParser(imgReader, false);

            this.hunkFile = parse.Parse();
            BuildSegments();
            this.firstCodeHunk = parse.FindFirstCodeHunk();
            var image = new LoadedImage(addrLoad, RelocateBytes(addrLoad));

            return(new Program(
                       image,
                       image.CreateImageMap(),
                       arch,
                       cfgSvc.GetEnvironment("amigaOS").Load(Services, arch)));
        }
Пример #12
0
        private void ProcessJumpTable(uint jtOffset)
        {
            var         j  = new JumpTable();
            ImageReader ir = new BeImageReader(image, jtOffset);

            j.AboveA5Size     = ir.ReadBeUInt32();
            j.BelowA5Size     = ir.ReadBeUInt32();
            j.JumpTableSize   = ir.ReadBeUInt32();
            j.JumpTableOffset = ir.ReadBeUInt32();
            uint size = j.JumpTableSize;

            while (size > 0)
            {
                JumpTableEntry jte = new JumpTableEntry();
                jte.RoutineOffsetFromSegmentStart = ir.ReadBeUInt16();
                jte.Instruction       = ir.ReadBeUInt32();
                jte.LoadSegTrapNumber = ir.ReadBeUInt16();
                Debug.WriteLine(string.Format("Jump table entry: {0:x2} {1:X4} {2:X2}", jte.RoutineOffsetFromSegmentStart, jte.Instruction, jte.LoadSegTrapNumber));
                size -= 8;
            }
        }
Пример #13
0
        public override Program Load(Address addrLoad)
        {
            var cfgSvc = Services.RequireService <IConfigurationService>();

            arch = (M68kArchitecture)cfgSvc.GetArchitecture("m68k");
            var imgReader = new BeImageReader(RawImage, 0);
            var parse     = new HunkFileParser(imgReader, false);

            this.hunkFile = parse.Parse();
            BuildSegments();
            this.firstCodeHunk = parse.FindFirstCodeHunk();
            var mem = new MemoryArea(addrLoad, RelocateBytes(addrLoad));

            return(new Program(
                       new ImageMap(
                           mem.BaseAddress,
                           new ImageSegment(
                               "code", mem, AccessMode.ReadWriteExecute)),
                       arch,
                       cfgSvc.GetEnvironment("amigaOS").Load(Services, arch)));
        }
Пример #14
0
        private Program LoadExecSegments(BeImageReader rdr)
        {
            var segments   = new List <ImageSegment>();
            var execAuxRdr = new StructureReader <SOM_Exec_aux_hdr>(rdr);
            var execAux    = execAuxRdr.Read();

            var cfgSvc = Services.RequireService <IConfigurationService>();
            var arch   = cfgSvc.GetArchitecture("paRisc");

            var dlHeaderRdr = ReadDynamicLibraryInfo(execAux, arch);

            var textBytes = new byte[execAux.exec_tsize];
            var textAddr  = Address.Ptr32(execAux.exec_tmem);

            Array.Copy(RawImage, (int)execAux.exec_tfile, textBytes, 0, textBytes.Length);
            var textSeg = new ImageSegment(
                ".text",
                new MemoryArea(textAddr, textBytes),
                AccessMode.ReadExecute);

            segments.Add(textSeg);

            var dataBytes = new byte[execAux.exec_dsize];
            var dataAddr  = Address.Ptr32(execAux.exec_tmem);

            Array.Copy(RawImage, (int)execAux.exec_dfile, dataBytes, 0, dataBytes.Length);
            var dataSeg = new ImageSegment(
                ".data",
                new MemoryArea(dataAddr, dataBytes),
                AccessMode.ReadWrite);

            segments.Add(dataSeg);

            var segmap = new SegmentMap(
                segments.Min(s => s.Address),
                segments.ToArray());
            var platform = cfgSvc.GetEnvironment("hpux").Load(Services, arch);

            return(new Program(segmap, arch, platform));
        }
Пример #15
0
        private ImageSegment LoadSegment(BeImageReader rdr)
        {
            var section = rdr.ReadStruct <Section>();
            var name    = Utf8StringFromFixedArray(section.s_name);
            var addr    = Address.Ptr32(section.v_paddr);
            var bytes   = new byte[section.s_size];

            if (section.s_scnptr != 0)
            {
                Array.Copy(RawImage, section.s_scnptr, bytes, 0, bytes.Length);
            }
            var mem    = new ByteMemoryArea(addr, bytes);
            var access = SectionAccessMode(section.s_flags);
            var seg    = new ImageSegment(name, mem, access);

            Debug.Print("   {0} {1,-10} {2}", seg.Address, section.s_flags, seg.Name);
            SetWellKnownSection(section, SectionFlags.STYP_TEXT, seg, ref textSection);
            SetWellKnownSection(section, SectionFlags.STYP_DATA, seg, ref dataSection);
            SetWellKnownSection(section, SectionFlags.STYP_BSS, seg, ref bssSection);
            SetWellKnownSection(section, SectionFlags.STYP_LOADER, seg, ref loaderSection);
            return(seg);
        }
Пример #16
0
        public override Program LoadProgram(Address?addrLoad)
        {
            var rdr    = new BeImageReader(RawImage);
            var header = rdr.ReadStruct <filehdr>();

            if (header.f_opthdr != 0)
            {
                var sectionOffset = rdr.Offset + header.f_opthdr;
                opthdr     = rdr.ReadStruct <aouthdr>();
                rdr.Offset = sectionOffset;
            }
            var sections = new scnhdr[header.f_nscns];

            for (int i = 0; i < sections.Length; ++i)
            {
                sections[i] = rdr.ReadStruct <scnhdr>();
            }
            var imgSegments = new ImageSegment[header.f_nscns];

            for (int i = 0; i < sections.Length; ++i)
            {
                imgSegments[i] = LoadImageSegment(sections[i]);
            }

            var arch     = LoadArchitecture(header.f_magic);
            var platform = new DefaultPlatform(Services, arch);
            var segmap   = new SegmentMap(imgSegments);
            var program  = new Program(segmap, arch, platform);

            if (this.opthdr.HasValue)
            {
                var addrEntry = Address.Ptr32(opthdr.Value.entry);   //$64
                var ep        = ImageSymbol.Procedure(program.Architecture, addrEntry, "_start");
                program.EntryPoints.Add(ep.Address, ep);
            }
            return(program);
        }
Пример #17
0
        public override Program LoadProgram(Address?addrLoad)
        {
            var rdr = new BeImageReader(this.RawImage, 0);

            LoadElfIdentification(rdr);
            this.innerLoader = CreateLoader();
            this.innerLoader.LoadArchitectureFromHeader();
            var platform = innerLoader.LoadPlatform(osAbi, innerLoader.Architecture);

            int cHeaders = innerLoader.LoadSegments();

            innerLoader.Sections.AddRange(innerLoader.LoadSectionHeaders());
            innerLoader.LoadSymbolsFromSections();
            //innerLoader.Dump();           // This spews a lot into the unit test output.
            Program program;

            if (cHeaders > 0)
            {
                program = innerLoader.LoadImage(platform, RawImage);
            }
            else
            {
                if (addrLoad != null)
                {
                    addrLoad = innerLoader.CreateAddress(addrLoad.ToLinear());
                }
                innerLoader.Dump(addrLoad ?? innerLoader.CreateAddress(0), Console.Out);

                // The file we're loading is an object file, and needs to be
                // linked before we can load it.
                var linker = innerLoader.CreateLinker();
                program = linker.LinkObject(platform, addrLoad, RawImage);
            }
            innerLoader !.Relocate(program, addrLoad !);
            return(program);
        }
Пример #18
0
        private int GetRunLengthValue(BeImageReader a5dr, ref int a5repeat)
        {
            // Run length returned is in byte(s).
            // next byte read - see bit pattern from the following table for the return value
            // 0xxxxxxx - 0 - $7F
            // 10xxxxxx - 0 - $3FFF(run length and $3F + next byte, 14 bits)
            // 110xxxxx - 0 - $1FFFFF(run length and $1F + next two bytes, 21 bits)
            // 1110xxxx - next 4 bytes, 32 bits
            // 1111xxxx - get both new runtime length copy in bytes and new runtime length repeat count

            int runLength = a5dr.ReadByte();

            if ((runLength & 0x80) == 0)
            {
                return(runLength);
            }
            if ((runLength & 0x40) == 0)
            {
                runLength = runLength & 0x3F;
                runLength = (runLength << 8) + a5dr.ReadByte();
                return(runLength);
            }
            if ((runLength & 0x20) == 0)
            {
                runLength = runLength & 0x1F;
                runLength = (runLength << 16) + a5dr.ReadBeInt16();
                return(runLength);
            }
            if ((runLength & 0x10) == 0)
            {
                return(a5dr.ReadBeInt32());
            }
            runLength = GetRunLengthValue(a5dr, ref a5repeat);
            a5repeat  = GetRunLengthValue(a5dr, ref a5repeat);
            return(runLength);
        }
Пример #19
0
 public XexLoader(IServiceProvider services, ImageLocation imageUri, byte[] imgRaw) : base(services, imageUri, imgRaw)
 {
     decompilerEventListener = services.RequireService <DecompilerEventListener>();
     rdr = new BeImageReader(RawImage, 0);
 }
Пример #20
0
        public void LoadElfIdentification()
        {
            var rdr = new BeImageReader(base.RawImage, 0);

            LoadElfIdentification(rdr);
        }
Пример #21
0
 public A5Relocator(MacOSClassic platform, BeImageReader a5dr, UInt32 a5dbelow)
 {
     this.platform = platform;
     this.a5dr     = a5dr;
     this.a5dbelow = a5dbelow;
 }
Пример #22
0
        public void Relocate()
        {
            var  memA5          = (ByteMemoryArea)platform.A5World.MemoryArea;
            var  a5belowWriter  = new BeImageWriter(memA5, 0);
            var  a5belowReader  = new BeImageReader(memA5, 0);
            uint a5globalOffset = platform.A5Offset - a5dbelow;

            var a5WorldAddress = (UInt32)((platform.A5World.Address.Offset + platform.A5Offset) & 0xFFFFFFFF);

            // set Repeat count = 1, reset after each completed copy cycle
            // byte token lower 4 bits number of words to copy from compressed data
            // byte token upper 4 bits number of words to skip in global application data space
            // if either value is 0 then get run length value which is in bytes.
            // if the new run length value for copy is 0 then it's the end of compression data.

            for (;;)
            {
                int a5repeat = 1;
                // Skip is number of 16-bit words to skip
                uint a5globalSkip = a5dr.ReadByte();
                if (a5globalSkip == 0)
                {
                    a5globalSkip = a5dr.ReadByte();
                    if (a5globalSkip == 0)
                    {
                        break;
                    }
                    if (a5globalSkip > 0x7F)
                    {
                        a5globalSkip = ((a5globalSkip & 0x7F) << 8) + a5dr.ReadByte();
                        a5globalSkip = (a5globalSkip << 16) + a5dr.ReadBeUInt16();
                    }
                    else
                    {
                        a5repeat = ResourceFork.GetRunLengthValue(a5dr, ref a5repeat);
                        //$BUG: a5repeat could return the value 0. The do-while below will
                        // decrement a5repeat before testing. This will lead to an effective
                        // repeat count of 2^32; likely not wanted.
                    }
                }
                else
                {
                    if ((a5globalSkip & 0x80) == 0x80)
                    {
                        a5globalSkip = ((a5globalSkip & 0x7F) << 8) + a5dr.ReadByte();
                    }
                }
                a5globalSkip = a5globalSkip * 2;
                do
                {
                    a5globalOffset += a5globalSkip;
                    a5belowReader.Seek(a5globalOffset, SeekOrigin.Begin);
                    uint a5ptrOffset = a5belowReader.ReadBeUInt32();
                    a5belowWriter.Position = (int)a5globalOffset;

                    // write relocated A5World pointers to absolute address in A5World segment
                    // Possible register/mark as Global pointer references to strings

                    a5belowWriter.WriteBeUInt32((a5WorldAddress + a5ptrOffset) & 0xFFFFFFFF);
                    --a5repeat;
                } while (a5repeat > 0);
            }
        }
Пример #23
0
        private void LoadPEImage()
        {
            long fileDataSize = rdr.Bytes.Length - xexData.header.header_size;

            BeImageReader memRdr    = new BeImageReader(xexData.memoryData);
            DOSHeader     dosHeader = memRdr.ReadStruct <DOSHeader>();

            dosHeader.Validate();

            memRdr.Offset = dosHeader.e_lfanew;

            UInt32 peSignature = memRdr.ReadUInt32();

            if (peSignature != 0x50450000)
            {
                throw new BadImageFormatException("PE: Invalid or Missing PE Signature");
            }

            COFFHeader coffHeader = memRdr.ReadStruct <COFFHeader>();

            if (coffHeader.Machine != 0x1F2)
            {
                throw new BadImageFormatException($"PE: Machine type does not match Xbox360 (found 0x{coffHeader.Machine:X})");
            }

            if ((coffHeader.Characteristics & 0x0100) == 0)
            {
                throw new BadImageFormatException("PE: Only 32-bit images are supported");
            }

            if (coffHeader.SizeOfOptionalHeader != 224)
            {
                throw new BadImageFormatException($"PE: Invalid size of optional header (got {coffHeader.SizeOfOptionalHeader}");
            }

            PEOptHeader optHeader = memRdr.ReadStruct <PEOptHeader>();

            if (optHeader.signature != 0x10b)
            {
                throw new BadImageFormatException($"PE: Invalid signature of optional header (got 0x{optHeader.signature})");
            }

            if (optHeader.Subsystem != IMAGE_SUBSYSTEM_XBOX)
            {
                throw new BadImageFormatException($"PE: Invalid subsystem (got {optHeader.Subsystem})");
            }

            xexData.peHeader = optHeader;

            uint extendedMemorySize = 0;
            uint numSections        = coffHeader.NumberOfSections;

            List <PESection> peSections = new List <PESection>();

            for (uint i = 0; i < numSections; i++)
            {
                COFFSection section = memRdr.ReadStruct <COFFSection>();

                string sectionName = Encoding.ASCII.GetString(section.Name).Trim('\0');

                uint lastMemoryAddress = section.VirtualAddress + section.VirtualSize;
                if (lastMemoryAddress > extendedMemorySize)
                {
                    extendedMemorySize = lastMemoryAddress;
                }

                if (section.SizeOfRawData == 0)
                {
                    decompilerEventListener.Info(new NullCodeLocation(""),
                                                 $"Skipping empty section {sectionName}"
                                                 );
                    continue;
                }

                byte[] sectionData = memRdr.ReadAt <byte[]>(section.PointerToRawData, rdr => rdr.ReadBytes(section.SizeOfRawData));

                AccessMode acc = AccessMode.Read;
                if (section.Flags.HasFlag(PESectionFlags.IMAGE_SCN_MEM_WRITE))
                {
                    acc |= AccessMode.Write;
                }
                if (section.Flags.HasFlag(PESectionFlags.IMAGE_SCN_MEM_EXECUTE))
                {
                    acc |= AccessMode.Execute;
                }

                PESection managedSection = new PESection(section);
                peSections.Add(managedSection);

                ImageSegment seg = new ImageSegment(sectionName, new MemoryArea(
                                                        new Address32(managedSection.PhysicalOffset + xexData.exe_address), sectionData
                                                        ), acc);
                segments.Add(seg);
            }

            if (extendedMemorySize > xexData.memorySize)
            {
                decompilerEventListener.Info(new NullCodeLocation(""),
                                             $"PE: Image sections extend beyond virtual memory range loaded from file ({extendedMemorySize} > {xexData.memorySize}). Extending by {extendedMemorySize - xexData.memorySize} bytes."
                                             );

                UInt32 oldMemorySize = xexData.memorySize;

                byte[] newMemoryData = new byte[extendedMemorySize];
                Array.Copy(xexData.memoryData, newMemoryData, xexData.memorySize);
                xexData.memorySize = extendedMemorySize;
                xexData.memoryData = newMemoryData;

                for (int i = 0; i < peSections.Count; i++)
                {
                    PESection section = peSections[i];

                    if (section.PhysicalSize == 0)
                    {
                        continue;
                    }

                    if (section.PhysicalSize + section.PhysicalOffset > fileDataSize)
                    {
                        decompilerEventListener.Warn(new NullCodeLocation(""),
                                                     $"PE: Section '{section.Name}' lies outside any phyisical data we have {section.PhysicalOffset} (size {section.PhysicalSize})"
                                                     );
                        continue;
                    }

                    if (section.VirtualOffset >= oldMemorySize)
                    {
                        uint sizeToCopy = section.PhysicalSize;
                        if (section.VirtualSize < sizeToCopy)
                        {
                            sizeToCopy = section.VirtualSize;
                        }

                        Array.Copy(
                            xexData.memoryData, section.PhysicalOffset,
                            newMemoryData, section.VirtualOffset,
                            sizeToCopy);
                    }
                }
            }
        }
Пример #24
0
 public XexLoader(IServiceProvider services, string filename, byte[] imgRaw) : base(services, filename, imgRaw)
 {
     decompilerEventListener = services.RequireService <DecompilerEventListener>();
     rdr = new BeImageReader(RawImage, 0);
 }
Пример #25
0
        private void A5Expand(BeImageReader a5dr, UInt32 a5dbelow)
        {
            var  a5belowWriter       = new BeImageWriter(platform.A5World.MemoryArea, platform.A5Offset - a5dbelow);
            int  a5RunLengthToken    = 0;
            int  a5RunLengthCopySize = 0;
            int  a5globalSkip        = 0;
            int  a5repeat            = 0;
            var  a5copylength        = 0;
            bool a5dataEnd           = false;

            // Compressed data
            // set Repeat count = 1, reset after each completed copy cycle
            // byte token lower 4 bits number of words to copy from compressed data
            // byte token upper 4 bits number of words to skip in global application data space
            // if either value is 0 then get run length value which is in bytes.
            // if the new run length value for copy is 0 then it's the end of compression data.

            do
            {
                a5repeat = 1;
                // Token value - upper nibble is words to skip, lower nibble is words to copy
                a5RunLengthToken    = a5dr.ReadByte();
                a5globalSkip        = a5RunLengthToken;
                a5RunLengthCopySize = a5RunLengthToken & 0x0F;
                if (a5RunLengthCopySize == 0)
                {
                    a5RunLengthCopySize = GetRunLengthValue(a5dr, ref a5repeat);
                    if (a5RunLengthCopySize == 0)
                    {
                        a5dataEnd = true;
                    }
                }
                else
                {
                    a5RunLengthCopySize = a5RunLengthCopySize * 2;
                }
                if (!a5dataEnd)
                {
                    a5globalSkip = a5globalSkip & 0xF0;
                    if (a5globalSkip == 0)
                    {
                        a5globalSkip = GetRunLengthValue(a5dr, ref a5repeat);
                    }
                    else
                    {
                        // convert value 0x01 - 0x0F number of words to skip in upper nibble to number of bytes to skip
                        a5globalSkip = a5globalSkip >> 3;
                    }
                    do
                    {
                        a5belowWriter.Position = a5belowWriter.Position + a5globalSkip;
                        a5copylength           = a5RunLengthCopySize;
                        do
                        {
                            a5belowWriter.WriteByte(a5dr.ReadByte());
                            a5copylength -= 1;
                        } while (a5copylength > 0);
                        a5repeat -= 1;
                    } while (a5repeat > 0);
                }
            } while (!a5dataEnd);
        }
Пример #26
0
 public MacsBugSymbolScanner(MemoryArea mem)
 {
     this.rdr = mem.CreateBeReader(0);
     this.reValidVariableLengthProcedureName = new Regex(
         "[a-zA-Z%_]([a-zA-Z0-9%_.])*");
 }
Пример #27
0
        public override Program Load(Address addrLoad, IProcessorArchitecture arch, IPlatform platform)
        {
            BeImageReader rdr = new BeImageReader(this.RawImage, 0);
            DolStructure? str = new StructureReader <DolStructure>(rdr).Read();

            if (!str.HasValue)
            {
                throw new BadImageFormatException("Invalid DOL header.");
            }
            this.hdr = new DolHeader(str.Value);
            var segments = new List <ImageSegment>();

            // Create code segments
            for (uint i = 0, snum = 1; i < 7; i++, snum++)
            {
                if (hdr.addressText[i] == Address32.NULL)
                {
                    continue;
                }
                var bytes = new byte[hdr.sizeText[i]];
                Array.Copy(RawImage, hdr.offsetText[i], bytes, 0, bytes.Length);
                var mem = new MemoryArea(hdr.addressText[i], bytes);
                segments.Add(new ImageSegment(
                                 string.Format("Text{0}", snum),
                                 mem,
                                 AccessMode.ReadExecute));
            }

            // Create all data segments
            for (uint i = 0, snum = 1; i < 11; i++, snum++)
            {
                if (hdr.addressData[i] == Address32.NULL ||
                    hdr.sizeData[i] == 0)
                {
                    continue;
                }
                var bytes = new byte[hdr.sizeData[i]];
                Array.Copy(RawImage, hdr.offsetData[i], bytes, 0, bytes.Length);
                var mem = new MemoryArea(hdr.addressText[i], bytes);

                segments.Add(new ImageSegment(
                                 string.Format("Data{0}", snum),
                                 mem,
                                 AccessMode.ReadWrite));
            }

            if (hdr.addressBSS != Address32.NULL)
            {
                segments.Add(new ImageSegment(
                                 ".bss",
                                 new MemoryArea(hdr.addressBSS, new byte[hdr.sizeBSS]),
                                 AccessMode.ReadWrite));
            }

            var segmentMap = new SegmentMap(addrLoad, segments.ToArray());

            var entryPoint = new ImageSymbol(this.hdr.entrypoint)
            {
                Type = SymbolType.Procedure
            };
            var program = new Program(
                segmentMap,
                arch,
                platform)
            {
                ImageSymbols = { { this.hdr.entrypoint, entryPoint } },
                EntryPoints  = { { this.hdr.entrypoint, entryPoint } }
            };

            return(program);
        }
Пример #28
0
        public override Program Load(Address addrLoad, IProcessorArchitecture arch, IPlatform platform)
        {
            BeImageReader rdr = new BeImageReader(this.RawImage, 0);

            try {
                this.hdr = new DolHeader(new StructureReader <DolStructure>(rdr).Read());
            } catch (Exception ex) {
                throw new BadImageFormatException("Invalid DOL header. " + ex.Message);
            }

            var segments = new List <ImageSegment>();

            // Create code segments
            for (uint i = 0, snum = 1; i < 7; i++, snum++)
            {
                if (hdr.addressText[i] == Address32.NULL)
                {
                    continue;
                }

                segments.Add(new ImageSegment(
                                 string.Format("Text{0}", snum),
                                 hdr.addressText[i], hdr.sizeText[i],
                                 AccessMode.ReadExecute
                                 ));
            }

            // Create all data segments
            for (uint i = 0, snum = 1; i < 11; i++, snum++)
            {
                if (hdr.addressData[i] == Address32.NULL)
                {
                    continue;
                }
                segments.Add(new ImageSegment(
                                 string.Format("Data{0}", snum),
                                 hdr.addressData[i], hdr.sizeData[i],
                                 AccessMode.ReadWrite
                                 ));
            }

            if (hdr.addressBSS != Address32.NULL)
            {
                segments.Add(new ImageSegment(
                                 ".bss",
                                 hdr.addressBSS, hdr.sizeBSS,
                                 AccessMode.ReadWrite
                                 ));
            }

            var segmentMap = new SegmentMap(addrLoad, segments.ToArray());

            var entryPoint = new ImageSymbol(this.hdr.entrypoint)
            {
                Type = SymbolType.Procedure
            };
            var program = new Program(
                segmentMap,
                arch,
                platform)
            {
                ImageSymbols = { { this.hdr.entrypoint, entryPoint } },
                EntryPoints  = { { this.hdr.entrypoint, entryPoint } }
            };

            return(program);
        }