1ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 2ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 3ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*--- begin libvex_guest_x86.h ---*/ 4ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 5ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 6ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* 7ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown This file is part of Valgrind, a dynamic binary instrumentation 8ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown framework. 9ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 10b32f58018498ea2225959b0ba11c18f0c433deefEvgeniy Stepanov Copyright (C) 2004-2011 OpenWorks LLP 11ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown info@open-works.net 12ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 13ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown This program is free software; you can redistribute it and/or 14ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown modify it under the terms of the GNU General Public License as 15ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown published by the Free Software Foundation; either version 2 of the 16ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown License, or (at your option) any later version. 17ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 18ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown This program is distributed in the hope that it will be useful, but 19ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown WITHOUT ANY WARRANTY; without even the implied warranty of 20ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 21ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown General Public License for more details. 22ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 23ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown You should have received a copy of the GNU General Public License 24ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown along with this program; if not, write to the Free Software 25ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 26ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 02110-1301, USA. 27ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 28ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown The GNU General Public License is contained in the file COPYING. 29ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 30ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Neither the names of the U.S. Department of Energy nor the 31ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown University of California nor the names of its contributors may be 32ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown used to endorse or promote products derived from this software 33ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown without prior written permission. 34ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown*/ 35ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 36ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#ifndef __LIBVEX_PUB_GUEST_X86_H 37ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define __LIBVEX_PUB_GUEST_X86_H 38ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 39ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include "libvex_basictypes.h" 40ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#include "libvex_emwarn.h" 41ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 42ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 43ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 44ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*--- Vex's representation of the x86 CPU state. ---*/ 45ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 46ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 47ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* The integer parts should be pretty straightforward. */ 48ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 49ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* Hmm, subregisters. The simulated state is stored in memory in the 50ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown host's byte ordering, so we can't say here what the offsets of %ax, 51ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown %al, %ah etc are since that depends on the host's byte ordering, 52ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown which we don't know. */ 53ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 54ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* FPU. For now, just simulate 8 64-bit registers, their tags, and 55ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown the reg-stack top pointer, of which only the least significant 56ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown three bits are relevant. 57ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 58ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown The model is: 59ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown F0 .. F7 are the 8 registers. FTOP[2:0] contains the 60ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown index of the current 'stack top' -- pretty meaningless, but 61ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown still. FTOP is a 32-bit value. FTOP[31:3] can be anything 62ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown (not guaranteed to be zero). 63ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 64ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown When a value is pushed onto the stack, ftop is first replaced by 65ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown (ftop-1) & 7, and then F[ftop] is assigned the value. 66ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 67ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown When a value is popped off the stack, the value is read from 68ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown F[ftop], and then ftop is replaced by (ftop+1) & 7. 69ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 70ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown In general, a reference to a register ST(i) actually references 71ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown F[ (ftop+i) & 7 ]. 72ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 73ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown FTAG0 .. FTAG0+7 are the tags. Each is a byte, zero means empty, 74ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown non-zero means non-empty. 75ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 76ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown The general rule appears to be that a read or modify of a register 77ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown gets a stack underflow fault if the register is empty. A write of 78ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown a register (only a write, not a modify) gets a stack overflow fault 79ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown if the register is full. Note that "over" vs "under" is pretty 80ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown meaningless since the FP stack pointer can move around arbitrarily, 81ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown so it's really just two different kinds of exceptions: 82ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown register-empty and register full. 83ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 84ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Naturally Intel (in its infinite wisdom) has seen fit to throw in 85ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown some ad-hoc inconsistencies to the fault-generation rules of the 86ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown above para, just to complicate everything. Known inconsistencies: 87ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 88ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown * fxam can read a register in any state without taking an underflow 89ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown fault. 90ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 91ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown * fst from st(0) to st(i) does not take an overflow fault even if the 92ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown destination is already full. 93ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 94ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown FPROUND[1:0] is the FPU's notional rounding mode, encoded as per 95ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown the IRRoundingMode type (see libvex_ir.h). This just happens to be 96ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown the Intel encoding. Note carefully, the rounding mode is only 97ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown observed on float-to-int conversions, and on float-to-float 98ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown rounding, but not for general float-to-float operations, which are 99ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown always rounded-to-nearest. 100ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 101ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Loads/stores of the FPU control word are faked accordingly -- on 102ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown loads, everything except the rounding mode is ignored, and on 103ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown stores, you get a vanilla control world (0x037F) with the rounding 104ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown mode patched in. Hence the only values you can get are 0x037F, 105ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 0x077F, 0x0B7F or 0x0F7F. Vex will emit an emulation warning if 106ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown you try and load a control word which either (1) unmasks FP 107ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown exceptions, or (2) changes the default (80-bit) precision. 108ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 109ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown FC3210 contains the C3, C2, C1 and C0 bits in the same place they 110ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown are in the FPU's status word. (bits 14, 10, 9, 8 respectively). 111ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown All other bits should be zero. The relevant mask to select just 112ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown those bits is 0x4700. To select C3, C2 and C0 only, the mask is 113ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 0x4500. 114ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 115ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown SSEROUND[1:0] is the SSE unit's notional rounding mode, encoded as 116ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown per the IRRoundingMode type. As with the FPU control word, the 117ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown rounding mode is the only part of %MXCSR that Vex observes. On 118ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown storing %MXCSR, you will get a vanilla word (0x1F80) with the 119ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown rounding mode patched in. Hence the only values you will get are 120ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 0x1F80, 0x3F80, 0x5F80 or 0x7F80. Vex will emit an emulation 121ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown warning if you try and load a control word which either (1) unmasks 122ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown any exceptions, (2) sets FZ (flush-to-zero) to 1, or (3) sets DAZ 123ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown (denormals-are-zeroes) to 1. 124ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 125ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Segments: initial prefixes of local and global segment descriptor 126ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown tables are modelled. guest_LDT is either zero (NULL) or points in 127ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown the host address space to an array of VEX_GUEST_X86_LDT_NENT 128ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown descriptors, which have the type VexGuestX86SegDescr, defined 129ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown below. Similarly, guest_GDT is either zero or points in the host 130ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown address space to an array of VEX_GUEST_X86_GDT_NENT descriptors. 131ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown The only place where these are used are in the helper function 132ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown x86g_use_seg(). LibVEX's client is responsible for pointing 133ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown guest_LDT and guest_GDT at suitable tables. The contents of these 134ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown tables are expected not to change during the execution of any given 135ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown superblock, but they may validly be changed by LibVEX's client in 136ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown between superblock executions. 137ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 138ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Since x86g_use_seg() only expects these tables to have 139ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown VEX_GUEST_X86_{LDT,GDT}_NENT entries, LibVEX's client should not 140ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown attempt to write entries beyond those limits. 141ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown*/ 142ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Browntypedef 143ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown struct { 144ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EAX; /* 0 */ 145ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_ECX; 146ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EDX; 147ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EBX; 148ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_ESP; 149ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EBP; 150ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_ESI; 151ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EDI; /* 28 */ 152ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 153ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* 4-word thunk used to calculate O S Z A C P flags. */ 154ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_CC_OP; /* 32 */ 155ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_CC_DEP1; 156ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_CC_DEP2; 157ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_CC_NDEP; /* 44 */ 158ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* The D flag is stored here, encoded as either -1 or +1 */ 159ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_DFLAG; /* 48 */ 160ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Bit 21 (ID) of eflags stored here, as either 0 or 1. */ 161ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_IDFLAG; /* 52 */ 162ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Bit 18 (AC) of eflags stored here, as either 0 or 1. */ 163ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_ACFLAG; /* 56 */ 164ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 165ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* EIP */ 166ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EIP; /* 60 */ 167ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 168ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* FPU */ 169ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown ULong guest_FPREG[8]; /* 64 */ 170ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UChar guest_FPTAG[8]; /* 128 */ 171ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_FPROUND; /* 136 */ 172ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_FC3210; /* 140 */ 173ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_FTOP; /* 144 */ 174ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 175ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* SSE */ 176ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_SSEROUND; /* 148 */ 177ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM0; /* 152 */ 178ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM1; 179ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM2; 180ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM3; 181ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM4; 182ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM5; 183ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM6; 184ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown U128 guest_XMM7; 185ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 186ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Segment registers. */ 187ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_CS; 188ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_DS; 189ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_ES; 190ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_FS; 191ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_GS; 192ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort guest_SS; 193ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* LDT/GDT stuff. */ 194ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown HWord guest_LDT; /* host addr, a VexGuestX86SegDescr* */ 195ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown HWord guest_GDT; /* host addr, a VexGuestX86SegDescr* */ 196ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 197ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Emulation warnings */ 198ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_EMWARN; 199ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 200ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* For clflush: record start and length of area to invalidate */ 201ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_TISTART; 202ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_TILEN; 203ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 204ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Used to record the unredirected guest address at the start of 205ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown a translation whose start has been redirected. By reading 206ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown this pseudo-register shortly afterwards, the translation can 207ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown find out what the corresponding no-redirection address was. 208ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown Note, this is only set for wrap-style redirects, not for 209ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown replace-style ones. */ 210ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_NRADDR; 211ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 212ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Used for Darwin syscall dispatching. */ 213ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_SC_CLASS; 214ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 215ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Needed for Darwin (but mandated for all guest architectures): 216ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown EIP at the last syscall insn (int 0x80/81/82, sysenter, 217ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown syscall). Used when backing up to restart a syscall that has 218ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown been interrupted by a signal. */ 219ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt guest_IP_AT_SYSCALL; 220ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 221ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /* Padding to make it have an 16-aligned size */ 222ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt padding1; 223ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt padding2; 224ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt padding3; 225ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown } 226ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown VexGuestX86State; 227ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 228ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define VEX_GUEST_X86_LDT_NENT /*64*/ 8192 /* use complete LDT */ 229ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#define VEX_GUEST_X86_GDT_NENT /*16*/ 8192 /* use complete GDT */ 230ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 231ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 232ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 233ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*--- Types for x86 guest stuff. ---*/ 234ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 235ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 236ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* VISIBLE TO LIBRARY CLIENT */ 237ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 238ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* This is the hardware-format for a segment descriptor, ie what the 239ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown x86 actually deals with. It is 8 bytes long. It's ugly. */ 240ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 241ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Browntypedef struct { 242ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown union { 243ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown struct { 244ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort LimitLow; 245ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UShort BaseLow; 246ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt BaseMid : 8; 247ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Type : 5; 248ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Dpl : 2; 249ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Pres : 1; 250ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt LimitHi : 4; 251ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Sys : 1; 252ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Reserved_0 : 1; 253ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Default_Big : 1; 254ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt Granularity : 1; 255ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt BaseHi : 8; 256ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown } Bits; 257ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown struct { 258ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt word1; 259ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown UInt word2; 260ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown } Words; 261ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown } 262ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown LdtEnt; 263ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown} VexGuestX86SegDescr; 264ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 265ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 266ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 267ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*--- Utility functions for x86 guest stuff. ---*/ 268ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 269ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 270ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* ALL THE FOLLOWING ARE VISIBLE TO LIBRARY CLIENT */ 271ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 272ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* Initialise all guest x86 state. The FPU is put in default mode. */ 273ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownextern 274ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid LibVEX_GuestX86_initialise ( /*OUT*/VexGuestX86State* vex_state ); 275ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 276ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 277ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* Extract from the supplied VexGuestX86State structure the 278ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown corresponding native %eflags value. */ 279ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownextern 280ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff BrownUInt LibVEX_GuestX86_get_eflags ( /*IN*/VexGuestX86State* vex_state ); 281ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 282ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/* Set the carry flag in the given state to 'new_carry_flag', which 283ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown should be zero or one. */ 284ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownextern 285ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brownvoid 286ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff BrownLibVEX_GuestX86_put_eflag_c ( UInt new_carry_flag, 287ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown /*MOD*/VexGuestX86State* vex_state ); 288ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 289ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown#endif /* ndef __LIBVEX_PUB_GUEST_X86_H */ 290ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown 291ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 292ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*--- libvex_guest_x86.h ---*/ 293ed07e00d438c74b7a23c01bfffde77e3968305e4Jeff Brown/*---------------------------------------------------------------*/ 294