Example #1
0
        StackFrame unwind_method(StackFrame frame, TargetMemoryAccess memory, byte[] code,
					  int pos, int offset)
        {
            Registers old_regs = frame.Registers;
            Registers regs = CopyRegisters (old_regs);

            if (!old_regs [(int) X86_Register.RBP].Valid)
                return null;

            TargetAddress rbp = new TargetAddress (
                memory.AddressDomain, old_regs [(int) X86_Register.RBP].Value);

            int addr_size = TargetAddressSize;
            TargetAddress new_rbp = memory.ReadAddress (rbp);
            regs [(int) X86_Register.RBP].SetValue (rbp, new_rbp);

            TargetAddress new_rip = memory.ReadAddress (rbp + addr_size);
            regs [(int) X86_Register.RIP].SetValue (rbp + addr_size, new_rip);

            TargetAddress new_rsp = rbp + 2 * addr_size;
            regs [(int) X86_Register.RSP].SetValue (rbp, new_rsp);

            rbp -= addr_size;

            int length = System.Math.Min (code.Length, offset);
            while (pos < length) {
                byte opcode = code [pos++];

                long value;
                if ((opcode == 0x41) && (pos < length)) {
                    byte opcode2 = code [pos++];

                    if ((opcode2 < 0x50) || (opcode2 > 0x57))
                        break;

                    switch (opcode2) {
                    case 0x50: /* r8 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R8].SetValue (rbp, value);
                        break;
                    case 0x51: /* r9 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R9].SetValue (rbp, value);
                        break;
                    case 0x52: /* r10 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R10].SetValue (rbp, value);
                        break;
                    case 0x53: /* r11 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R11].SetValue (rbp, value);
                        break;
                    case 0x54: /* r12 */
                        value = (long) memory.ReadAddress (rbp).Address;
                        regs [(int) X86_Register.R12].SetValue (rbp, value);
                        break;
                    case 0x55: /* r13 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R13].SetValue (rbp, value);
                        break;
                    case 0x56: /* r14 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R14].SetValue (rbp, value);
                        break;
                    case 0x57: /* r15 */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.R15].SetValue (rbp, value);
                        break;
                    }
                } else {
                    if ((opcode < 0x50) || (opcode > 0x57))
                        break;

                    switch (opcode) {
                    case 0x50: /* rax */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RAX].SetValue (rbp, value);
                        break;
                    case 0x51: /* rcx */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RCX].SetValue (rbp, value);
                        break;
                    case 0x52: /* rdx */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RDX].SetValue (rbp, value);
                        break;
                    case 0x53: /* rbx */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RBX].SetValue (rbp, value);
                        break;
                    case 0x56: /* rsi */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RSI].SetValue (rbp, value);
                        break;
                    case 0x57: /* rdi */
                        value = memory.ReadLongInteger (rbp);
                        regs [(int) X86_Register.RDI].SetValue (rbp, value);
                        break;
                    }
                }

                rbp -= addr_size;
            }

            return CreateFrame (frame.Thread, FrameType.Normal, memory, new_rip, new_rsp, new_rbp, regs);
        }
        StackFrame unwind_method(StackFrame frame, TargetMemoryAccess memory, byte[] code,
                                 int pos, int offset)
        {
            Registers old_regs = frame.Registers;
            Registers regs     = CopyRegisters(old_regs);

            if (!old_regs [(int)X86_Register.RBP].Valid)
            {
                return(null);
            }

            TargetAddress rbp = new TargetAddress(
                memory.AddressDomain, old_regs [(int)X86_Register.RBP].Value);

            int           addr_size = TargetAddressSize;
            TargetAddress new_rbp   = memory.ReadAddress(rbp);

            regs [(int)X86_Register.RBP].SetValue(rbp, new_rbp);

            TargetAddress new_rip = memory.ReadAddress(rbp + addr_size);

            regs [(int)X86_Register.RIP].SetValue(rbp + addr_size, new_rip);

            TargetAddress new_rsp = rbp + 2 * addr_size;

            regs [(int)X86_Register.RSP].SetValue(rbp, new_rsp);

            rbp -= addr_size;

            int length = System.Math.Min(code.Length, offset);

            while (pos < length)
            {
                byte opcode = code [pos++];

                long value;
                if ((opcode == 0x41) && (pos < length))
                {
                    byte opcode2 = code [pos++];

                    if ((opcode2 < 0x50) || (opcode2 > 0x57))
                    {
                        break;
                    }

                    switch (opcode2)
                    {
                    case 0x50:                     /* r8 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R8].SetValue(rbp, value);
                        break;

                    case 0x51:                     /* r9 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R9].SetValue(rbp, value);
                        break;

                    case 0x52:                     /* r10 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R10].SetValue(rbp, value);
                        break;

                    case 0x53:                     /* r11 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R11].SetValue(rbp, value);
                        break;

                    case 0x54:                     /* r12 */
                        value = (long)memory.ReadAddress(rbp).Address;
                        regs [(int)X86_Register.R12].SetValue(rbp, value);
                        break;

                    case 0x55:                     /* r13 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R13].SetValue(rbp, value);
                        break;

                    case 0x56:                     /* r14 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R14].SetValue(rbp, value);
                        break;

                    case 0x57:                     /* r15 */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.R15].SetValue(rbp, value);
                        break;
                    }
                }
                else
                {
                    if ((opcode < 0x50) || (opcode > 0x57))
                    {
                        break;
                    }

                    switch (opcode)
                    {
                    case 0x50:                     /* rax */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RAX].SetValue(rbp, value);
                        break;

                    case 0x51:                     /* rcx */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RCX].SetValue(rbp, value);
                        break;

                    case 0x52:                     /* rdx */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RDX].SetValue(rbp, value);
                        break;

                    case 0x53:                     /* rbx */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RBX].SetValue(rbp, value);
                        break;

                    case 0x56:                     /* rsi */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RSI].SetValue(rbp, value);
                        break;

                    case 0x57:                     /* rdi */
                        value = memory.ReadLongInteger(rbp);
                        regs [(int)X86_Register.RDI].SetValue(rbp, value);
                        break;
                    }
                }

                rbp -= addr_size;
            }

            return(CreateFrame(frame.Thread, FrameType.Normal, memory, new_rip, new_rsp, new_rbp, regs));
        }