public override ProcedureBase GetTrampolineDestination(ImageReader rdr, IRewriterHost host) { var rw = Architecture.CreateRewriter( rdr, Architecture.CreateProcessorState(), Architecture.CreateFrame(), host); var rtlc = rw.FirstOrDefault(); if (rtlc == null || rtlc.Instructions.Count == 0) return null; var jump = rtlc.Instructions[0] as RtlGoto; if (jump == null) return null; var pc = jump.Target as ProcedureConstant; if (pc != null) return pc.Procedure; var access = jump.Target as MemoryAccess; if (access == null) return null; var addrTarget = access.EffectiveAddress as Address; if (addrTarget == null) { var wAddr = access.EffectiveAddress as Constant; if (wAddr == null) { return null; } addrTarget = MakeAddressFromConstant(wAddr); } ProcedureBase proc = host.GetImportedProcedure(addrTarget, rtlc.Address); if (proc != null) return proc; return host.GetInterceptedCall(addrTarget); }
public GlobalDataWorkItem(IScanner scanner, Program program, Address addr, DataType dt) : base(addr) { this.scanner = scanner; this.program = program; this.dt = dt; this.rdr = program.CreateImageReader(addr); }
public List<ProgramResource> ReadLanguageDirectory(ImageReader rdr, uint resourceType, string resourceId) { const uint DIR_MASK = 0x80000000; var flags = rdr.ReadUInt32(); var date = rdr.ReadUInt32(); var version = rdr.ReadUInt32(); var cNameEntries = rdr.ReadUInt16(); var cIdEntries = rdr.ReadUInt16(); var entries = new List<ProgramResource>(); for (int i = 0; i < cNameEntries; ++i) { var rvaName = rdr.ReadUInt32(); var rvaEntry = rdr.ReadUInt32(); var subRdr = new LeImageReader(imgLoaded, rvaResources + (rvaEntry & ~DIR_MASK)); if ((rvaEntry & DIR_MASK) != 0) throw new BadImageFormatException(); entries.Add(ReadResourceEntry(subRdr, resourceId, ReadResourceString(rvaName), resourceType)); } for (int i = 0; i < cIdEntries; ++i) { var id = rdr.ReadUInt32(); var rvaEntry = rdr.ReadUInt32(); var subRdr = new LeImageReader(imgLoaded, rvaResources + (rvaEntry & ~DIR_MASK)); if ((rvaEntry & DIR_MASK) != 0) throw new BadImageFormatException(); entries.Add(ReadResourceEntry(subRdr, resourceId, id.ToString(), resourceType)); } return entries; }
public override void ApplyRelocation(Address baseOfImage, uint page, ImageReader rdr, RelocationDictionary relocations) { ushort fixup = rdr.ReadLeUInt16(); Address offset = baseOfImage + page + (fixup & 0x0FFFu); var imgR = program.CreateImageReader(offset); var imgW = program.CreateImageWriter(offset); switch (fixup >> 12) { case RelocationAbsolute: // Used for padding to 4-byte boundary, ignore. break; case RelocationHighLow: { uint n = (uint) (imgR.ReadUInt32() + (baseOfImage - program.ImageMap.BaseAddress)); imgW.WriteUInt32(n); relocations.AddPointerReference(offset.ToLinear() - imgW.MemoryArea.BaseAddress.ToLinear(), n); break; } case 0xA: break; default: dcSvc.Warn( dcSvc.CreateAddressNavigator(program, offset), string.Format( "Unsupported i386 PE fixup type: {0:X}", fixup >> 12)); break; } }
public IEnumerable<RtlInstructionCluster> CreateRewriter(ImageReader rdr, ProcessorState state, Frame frame, IRewriterHost host) { var linAddr = rdr.Address.ToLinear(); RtlTrace trace; if (!rewriters.Traces.TryGetValue(rdr.Address, out trace)) NUnit.Framework.Assert.Fail(string.Format("Unexpected request for a rewriter at address {0}", rdr.Address)); return trace; }
private void CreateDisassembler16(ImageReader rdr) { dasm = new X86Disassembler( rdr, PrimitiveType.Word16, PrimitiveType.Word16, false); }
public override IEnumerable<RtlInstructionCluster> CreateRewriter(ImageReader rdr, ProcessorState state, Frame frame, IRewriterHost host) { return new MipsRewriter( this, new MipsDisassembler(this, rdr, IsVersion6OrLater), frame, host); }
public virtual object ReadValue(System.Reflection.FieldInfo f, ImageReader rdr, ReaderContext ctx) { Func<ImageReader, object> fn; if (readers.TryGetValue(f.FieldType, out fn)) { return fn(rdr); } throw new NotSupportedException(string.Format("Field type {0} not supported.", f.FieldType.FullName)); }
public override object ReadValue(FieldInfo f, ImageReader rdr, ReaderContext ctx) { int i = 0; for (; rdr.PeekByte(i) != 0; ++i) { } var s = Encoding.UTF8.GetString(rdr.ReadBytes(i)); rdr.Offset++; return s; }
public override IEnumerable<MachineInstruction> CreateDisassembler(ImageReader imageReader) { int i = prog.IndexOfKey(imageReader.Address.ToUInt16()); if (i < 0) yield break; for (; i < prog.Count; ++i) { yield return prog.Values[i]; } }
public static Elf32_Sym Load(ImageReader rdr) { var sym = new Elf32_Sym(); sym.st_name = rdr.ReadUInt32(); sym.st_value = rdr.ReadUInt32(); sym.st_size = rdr.ReadUInt32(); sym.st_info = rdr.ReadByte(); sym.st_other = rdr.ReadByte(); sym.st_shndx = rdr.ReadUInt16(); return sym; }
public static Elf64_Rela Read(ImageReader rdr) { var o = rdr.ReadUInt64(); var i = rdr.ReadUInt64(); var a = rdr.ReadInt64(); return new Elf64_Rela { r_offset = o, r_info = i, r_addend = a }; }
public void Read(ImageReader rdr) { foreach (var f in fields) { var attr = GetFieldAttribute(f); uint alignment = (uint) attr.Align; rdr.Offset = (rdr.Offset + alignment - 1u) & ~(alignment - 1u); Debug.Print("At offset: {0:X8} reading field '{1}.{2}' after alignment of {3}.", rdr.Offset, f.DeclaringType.Name, f.Name, alignment); object value = attr.ReadValue(f, rdr, null); f.SetValue(structure, value); } }
protected Address ReadSegmentedCodeAddress(int byteSize, ImageReader rdr, ProcessorState state) { if (byteSize == PrimitiveType.Word16.Size) { return Address.SegPtr(state.GetRegister(Registers.cs).ToUInt16(), rdr.ReadLeUInt16()); } else { ushort off = rdr.ReadLeUInt16(); ushort seg = rdr.ReadLeUInt16(); return Address.SegPtr(seg, off); } }
public static Elf64_PHdr Load(ImageReader rdr) { var hdr = new Elf64_PHdr { p_type = (ProgramHeaderType)rdr.ReadUInt32(), p_flags = rdr.ReadUInt32(), p_offset = rdr.ReadUInt64(), p_vaddr = rdr.ReadUInt64(), p_paddr = rdr.ReadUInt64(), p_filesz = rdr.ReadUInt64(), p_pmemsz = rdr.ReadUInt64(), p_align = rdr.ReadUInt64(), }; return hdr; }
public static Elf64_SHdr Load(ImageReader rdr) { return new Elf64_SHdr { sh_name = rdr.ReadUInt32(), sh_type = (SectionHeaderType)rdr.ReadUInt32(), sh_flags = rdr.ReadUInt64(), sh_addr = rdr.ReadUInt64(), // Address sh_offset = rdr.ReadUInt64(), sh_size = rdr.ReadUInt64(), sh_link = rdr.ReadUInt32(), sh_info = rdr.ReadUInt32(), sh_addralign = rdr.ReadUInt64(), sh_entsize = rdr.ReadUInt64(), }; }
public override IEnumerable<Address> CreatePointerScanner(ImageMap map, ImageReader rdr, IEnumerable<Address> knownAddresses, PointerScannerFlags flags) { var knownLinAddresses = knownAddresses.Select(a => a.ToUInt32()).ToHashSet(); if (flags != PointerScannerFlags.Calls) throw new NotImplementedException(string.Format("Haven't implemented support for scanning for {0} yet.", flags)); while (rdr.IsValid) { uint linAddrCall = rdr.Address.ToUInt32(); var opcode = rdr.ReadLeUInt32(); if ((opcode & 0x0F000000) == 0x0B000000) // BL { int offset = ((int)opcode << 8) >> 6; uint target = (uint)(linAddrCall + 8 + offset); if (knownLinAddresses.Contains(target)) yield return Address.Ptr32(linAddrCall); } } }
public ushort e_shstrndx; // section name string table index public static Elf32_EHdr Load(ImageReader rdr) { return new Elf32_EHdr { e_type = rdr.ReadUInt16(), e_machine = rdr.ReadUInt16(), e_version = rdr.ReadUInt32(), e_entry = rdr.ReadUInt32(), e_phoff = rdr.ReadUInt32(), e_shoff = rdr.ReadUInt32(), e_flags = rdr.ReadUInt32(), e_ehsize = rdr.ReadUInt16(), e_phentsize = rdr.ReadUInt16(), e_phnum = rdr.ReadUInt16(), e_shentsize = rdr.ReadUInt16(), e_shnum = rdr.ReadUInt16(), e_shstrndx = rdr.ReadUInt16(), }; }
public List<ProgramResource> ReadResourceDirectory(ImageReader rdr) { const uint DIR_MASK = 0x80000000; var flags = rdr.ReadUInt32(); var date = rdr.ReadUInt32(); var version = rdr.ReadUInt32(); var cNameEntries = rdr.ReadUInt16(); var cIdEntries = rdr.ReadUInt16(); var entries = new List<ProgramResource>(); for (int i = 0; i < cNameEntries; ++i) { var rvaName = rdr.ReadUInt32(); var rvaEntry = rdr.ReadUInt32(); var subRdr = new LeImageReader(imgLoaded, rvaResources + (rvaEntry & ~DIR_MASK)); if ((rvaEntry & DIR_MASK) == 0) throw new BadImageFormatException(); if ((rvaName & DIR_MASK) != 0) { var e = new ProgramResourceGroup { //Name = ReadResourceString(rvaName), Name = ReadResourceUtf16leString(rvaResources + (rvaName & ~DIR_MASK)), }; e.Resources.AddRange(ReadNameDirectory(subRdr, 0)); entries.Add(e); } } for (int i = 0; i < cIdEntries; ++i) { var id = rdr.ReadUInt32(); var rvaEntry = rdr.ReadUInt32(); var subRdr = new LeImageReader(imgLoaded, rvaResources + (rvaEntry & ~DIR_MASK)); if ((rvaEntry & DIR_MASK) == 0) throw new BadImageFormatException(); var e = new ProgramResourceGroup { Name = GenerateResourceName(id), }; e.Resources.AddRange(ReadNameDirectory(subRdr, id)); entries.Add(e); } return entries; }
public static object ReadPointer(Type pointerType, int size, ImageReader rdr, ReaderContext ctx) { Debug.Print("Reading pointer at offset {0}, size {1}", rdr.Offset, size); uint newOffset; switch (size) { default: throw new InvalidOperationException("Field size must be > 0."); case 1: newOffset = rdr.ReadByte(); break; case 2: newOffset = rdr.ReadUInt16(); break; case 4: newOffset = rdr.ReadUInt32(); break; } Debug.Print("Structure of type {0} must start at offset {1:X}", pointerType.Name, newOffset); rdr = rdr.Clone(); rdr.Offset = newOffset; var dst = Activator.CreateInstance(pointerType); var sr = new StructureReader(dst); sr.Read(rdr); return dst; }
public static Elf32_SHdr Load(ImageReader rdr) { try { return new Elf32_SHdr { sh_name = rdr.ReadUInt32(), sh_type = (SectionHeaderType)rdr.ReadUInt32(), sh_flags = rdr.ReadUInt32(), sh_addr = rdr.ReadUInt32(), // Address sh_offset = rdr.ReadUInt32(), sh_size = rdr.ReadUInt32(), sh_link = rdr.ReadUInt32(), sh_info = rdr.ReadUInt32(), sh_addralign = rdr.ReadUInt32(), sh_entsize = rdr.ReadUInt32(), }; } catch { //$TODO: report error? return null; } }
public const short IMAGE_REL_MIPS_PAIR = 0x0025; // This relocation is only valid when it immediately follows a REFHI or SECRELHI relocation. Its SymbolTableIndex contains a displacement and not an index into the symbol table. public override void ApplyRelocation(Address baseOfImage, uint page, ImageReader rdr, RelocationDictionary relocations) { ushort fixup = rdr.ReadUInt16(); Address offset = baseOfImage + page + (fixup & 0x0FFFu); var imgR = program.CreateImageReader(offset); var imgW = program.CreateImageWriter(offset); uint w = imgR.ReadUInt32(); int s; switch (fixup >> 12) { case IMAGE_REL_MIPS_ABSOLUTE: // Used for padding to 4-byte boundary, ignore. break; case IMAGE_REL_MIPS_REFWORD: break; case IMAGE_REL_MIPS_JMPADDR: break; case IMAGE_REL_MIPS_REFHI: w = imgR.ReadUInt32(); //w += (fixup & 0x0FFFu); //imgW.WriteUInt32(w); s = rdr.ReadInt16(); w = (uint)(w + s); // w points to something. break; case IMAGE_REL_MIPS_REFLO: // w points to something. break; default: dcSvc.Warn( dcSvc.CreateAddressNavigator(program, offset), string.Format( "Unsupported MIPS PE fixup type: {0:X}", fixup >> 12)); break; } }
public Enumerator(PointerScanner <T> scanner, ImageReader rdr) { this.scanner = scanner; this.r = rdr; }
/// <summary> /// The implementations of this abstract method should read a chunk of bytes /// equal to the size of an opcode in the relevant architecture. /// </summary> /// <remarks>Most architectures have opcode whose size <= 32 bits, which should /// fit comfortably in a System.UInt32.</remarks> /// <param name="rdr"></param> /// <returns>The opcode at the current position of the reader.</returns> public abstract bool TryPeekOpcode(ImageReader rdr, out uint opcode);
private T BytesToStruct <T>(ImageReader reader) { byte[] bytes = reader.ReadBytes(Marshal.SizeOf(typeof(T))); return(this.BytesToStruct <T>(bytes)); }
public override IEnumerable<Address> CreatePointerScanner( SegmentMap map, ImageReader rdr, IEnumerable<Address> knownAddresses, PointerScannerFlags flags) { var knownLinAddresses = knownAddresses .Select(a => a.ToLinear()) .ToHashSet(); return new PowerPcPointerScanner64(rdr, knownLinAddresses, flags) .Select(u => Address.Ptr64(u)); }
public static BinaryReader CreateBinaryImageReader(this ImageReader @rdr) { return(new BinaryReader(new ImageStream(rdr.Image))); }
/// <summary> /// /// </summary> /// <param name="rdr"></param> /// <returns></returns> public static BinaryReader CreateBinaryReader(this ImageReader @rdr) { return(new BinaryReader(new MemoryStream(rdr.Bytes))); }
public override IEnumerable<RtlInstructionCluster> CreateRewriter(ImageReader rdr, ProcessorState state, Frame frame, IRewriterHost host) { return new SparcRewriter(this, rdr, (SparcProcessorState)state, frame, host); }
public abstract bool MatchJump(ImageReader rdr, uint opcode, out T target);
public ImageStream(MemoryArea memArea) { this.mem = memArea; this.rdr = new ImageReader(memArea.Bytes); }
public PointerScanner(ImageReader rdr, HashSet <T> knownLinAddresses, PointerScannerFlags flags) { this.rdr = rdr; this.knownLinAddresses = knownLinAddresses; this.flags = flags; }
public TypedDataDumper(ImageReader rdr, uint cbSize, Formatter stm) { this.rdr = rdr; this.cbSize = cbSize; this.fmt = stm; }
public override Address ReadCodeAddress(int size, ImageReader rdr, ProcessorState state) { throw new NotImplementedException(); }
public abstract IEnumerable <MachineInstruction> CreateDisassembler(ImageReader imageReader);
public abstract IEnumerable <Address> CreatePointerScanner(ImageMap map, ImageReader rdr, IEnumerable <Address> knownAddresses, PointerScannerFlags flags);
public abstract bool TryPeekPointer(ImageReader rdr, out T target);
public override abstract IEnumerable<Address> CreatePointerScanner( SegmentMap map, ImageReader rdr, IEnumerable<Address> addrs, PointerScannerFlags flags);
public abstract IEnumerable <RtlInstructionCluster> CreateRewriter(ImageReader rdr, ProcessorState state, Frame frame, IRewriterHost host);
public override ProcedureBase GetTrampolineDestination(ImageReader imageReader, IRewriterHost host) { throw new NotImplementedException(); }
public abstract Address ReadCodeAddress(int size, ImageReader rdr, ProcessorState state);
public override ProcedureBase GetTrampolineDestination(ImageReader imageReader, IRewriterHost host) { return null; }
/// <summary> /// If the instructions located at the address the image reader is reading are a /// trampoline, returns the procedure where the destination is located, otherwise /// returns null. /// </summary> /// <param name="imageReader"></param> /// <returns></returns> public abstract ProcedureBase GetTrampolineDestination(ImageReader imageReader, IRewriterHost host);
public override IEnumerable<MachineInstruction> CreateDisassembler(ImageReader imageReader) { return new SparcDisassembler(this, imageReader); }
public override ProcedureBase GetTrampolineDestination(ImageReader imageReader, IRewriterHost host) { // No trampolines are supported. return(null); }
public override IEnumerable<Address> CreatePointerScanner(SegmentMap map, ImageReader rdr, IEnumerable<Address> knownAddresses, PointerScannerFlags flags) { throw new NotImplementedException(); }
public StructureReader(ImageReader reader) : this(reader.ReadBytes) { }