Exemple #1
0
        private static void Disasm(Stream stream, uint size, TextWriter writer, Formatter formatter = null)
        {
            var buffer = ArrayPool <byte> .Shared.Rent((int)size);

            var startPosition = stream.Position;

            stream.Read(buffer, 0, (int)size);
            stream.Position = startPosition;

            // You can also pass in a hex string, eg. "90 91 929394", or you can use your own CodeReader
            // reading data from a file or memory etc
            var codeReader = new StreamCodeReader(stream, size);
            var decoder    = Decoder.Create(IntPtr.Size * 8, codeReader);

            decoder.IP = (ulong)0;
            ulong endRip = decoder.IP + (uint)size;

            // This list is faster than List<Instruction> since it uses refs to the Instructions
            // instead of copying them (each Instruction is 32 bytes in size). It has a ref indexer,
            // and a ref iterator. Add() uses 'in' (ref readonly).
            var instructions = new InstructionList();

            while (decoder.IP < endRip)
            {
                // The method allocates an uninitialized element at the end of the list and
                // returns a reference to it which is initialized by Decode().
                decoder.Decode(out instructions.AllocUninitializedElement());
            }

            // Formatters: Masm*, Nasm* and Gas* (AT&T)
            if (formatter == null)
            {
                formatter = new NasmFormatter();
                formatter.Options.DigitSeparator        = "";
                formatter.Options.FirstOperandCharIndex = 10;
            }
            var output = new StringBuilderFormatterOutput();

            // Use InstructionList's ref iterator (C# 7.3) to prevent copying 32 bytes every iteration
            foreach (ref var instr in instructions)
            {
                // Don't use instr.ToString(), it allocates more, uses masm syntax and default options
                formatter.Format(instr, output);
                writer.Write($"{instr.IP:X16} ");
                for (int i = 0; i < instr.ByteLength; i++)
                {
                    writer.Write(buffer[(int)instr.IP + i].ToString("X2"));
                }
                writer.Write(new string(' ', 16 * 2 - instr.ByteLength * 2));
                writer.WriteLine($"{output.ToStringAndReset()}");
            }
        }
        public unsafe XrefScanner(IntPtr codeStart, int lengthLimit = 1000)
        {
            if (codeStart == IntPtr.Zero)
            {
                throw new NullReferenceException(nameof(codeStart));
            }

            myUnmanagedMemoryStream = new UnmanagedMemoryStream((byte *)codeStart, lengthLimit, lengthLimit, FileAccess.Read);
            var codeReader = new StreamCodeReader(myUnmanagedMemoryStream);

            myDecoder    = Decoder.Create(IntPtr.Size * 8, codeReader);
            myDecoder.IP = (ulong)codeStart;
        }
Exemple #3
0
        private static int CalcAsmLength(Assembler asm)
        {
            var stream = new MemoryStream();

            asm.Assemble(new StreamCodeWriter(stream), 0);

            // Disassemble the result
            stream.Position = 0;
            var reader  = new StreamCodeReader(stream);
            var decoder = Decoder.Create(64, reader);

            return(decoder.Select(i => i.Length).Sum());
        }
        internal static unsafe Decoder DecoderForAddress(IntPtr codeStart, int lengthLimit = 1000)
        {
            if (codeStart == IntPtr.Zero)
            {
                throw new NullReferenceException(nameof(codeStart));
            }

            var stream     = new UnmanagedMemoryStream((byte *)codeStart, lengthLimit, lengthLimit, FileAccess.Read);
            var codeReader = new StreamCodeReader(stream);
            var decoder    = Decoder.Create(IntPtr.Size * 8, codeReader);

            decoder.IP = (ulong)codeStart;

            return(decoder);
        }
Exemple #5
0
        private byte[] Assemble(Assembler assembler)
        {
            using var stream = new MemoryStream();
            assembler.Assemble(new StreamCodeWriter(stream), 0);

            stream.Position = 0;
            var reader = new StreamCodeReader(stream);

            int next;
            var bytes = new byte[stream.Length];

            while ((next = reader.ReadByte()) >= 0)
            {
                bytes[stream.Position - 1] = (byte)next;
            }

            return(bytes);
        }