📄 ghelpers.c
字号:
pair = amd64g_check_fldcw ( (ULong)fpucw ); fpround = pair & 0xFFFFFFFFULL; ew = (VexEmWarn)(pair >> 32); vex_state->guest_FPROUND = fpround & 3; /* emulation warnings --> caller */ return ew;}/* CALLED FROM GENERATED CODE *//* DIRTY HELPER *//* Create an x87 FPU env from the guest state, as close as we can approximate it. Writes 28 bytes at x87_state[0..27]. */void amd64g_dirtyhelper_FSTENV ( /*IN*/VexGuestAMD64State* vex_state, /*OUT*/HWord x87_state ){ Int i, stno, preg; UInt tagw; UChar* vexTags = (UChar*)(&vex_state->guest_FPTAG[0]); Fpu_State* x87 = (Fpu_State*)x87_state; UInt ftop = vex_state->guest_FTOP; ULong c3210 = vex_state->guest_FC3210; for (i = 0; i < 14; i++) x87->env[i] = 0; x87->env[1] = x87->env[3] = x87->env[5] = x87->env[13] = 0xFFFF; x87->env[FP_ENV_STAT] = toUShort(toUInt( ((ftop & 7) << 11) | (c3210 & 0x4700) )); x87->env[FP_ENV_CTRL] = toUShort(toUInt( amd64g_create_fpucw( vex_state->guest_FPROUND ) )); /* Compute the x87 tag word. */ tagw = 0; for (stno = 0; stno < 8; stno++) { preg = (stno + ftop) & 7; if (vexTags[preg] == 0) { /* register is empty */ tagw |= (3 << (2*preg)); } else { /* register is full. */ tagw |= (0 << (2*preg)); } } x87->env[FP_ENV_TAG] = toUShort(tagw); /* We don't dump the x87 registers, tho. */}/*---------------------------------------------------------------*//*--- Misc integer helpers, including rotates and CPUID. ---*//*---------------------------------------------------------------*//* Claim to be the following CPU: vendor_id : AuthenticAMD cpu family : 15 model : 12 model name : AMD Athlon(tm) 64 Processor 3200+ stepping : 0 cpu MHz : 2202.917 cache size : 512 KB fpu : yes fpu_exception : yes cpuid level : 1 wp : yes flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 pni syscall nx mmxext lm 3dnowext 3dnow bogomips : 4308.99 TLB size : 1088 4K pages clflush size : 64 cache_alignment : 64 address sizes : 40 bits physical, 48 bits virtual power management: ts fid vid ttp*/void amd64g_dirtyhelper_CPUID ( VexGuestAMD64State* st ){# define SET_ABCD(_a,_b,_c,_d) \ do { st->guest_RAX = (ULong)(_a); \ st->guest_RBX = (ULong)(_b); \ st->guest_RCX = (ULong)(_c); \ st->guest_RDX = (ULong)(_d); \ } while (0) switch (0xFFFFFFFF & st->guest_RAX) { case 0x0: SET_ABCD(0x00000001, 0x68747541, 0x444d4163, 0x69746e65); break; case 0x1: SET_ABCD(0x00000fc0, 0x00000800, 0x00000000, 0x078bfbff); break; case 0x80000000: SET_ABCD(0x80000018, 0x68747541, 0x444d4163, 0x69746e65); break; case 0x80000001: SET_ABCD(0x00000fc0, 0x0000010a, 0x00000000, 0xe1d3fbff); break; case 0x80000002: SET_ABCD(0x20444d41, 0x6c687441, 0x74286e6f, 0x3620296d); break; case 0x80000003: SET_ABCD(0x72502034, 0x7365636f, 0x20726f73, 0x30303233); break; case 0x80000004: SET_ABCD(0x0000002b, 0x00000000, 0x00000000, 0x00000000); break; case 0x80000005: SET_ABCD(0xff08ff08, 0xff20ff20, 0x40020140, 0x40020140); break; case 0x80000006: SET_ABCD(0x00000000, 0x42004200, 0x02008140, 0x00000000); break; case 0x80000007: SET_ABCD(0x00000000, 0x00000000, 0x00000000, 0x0000000f); break; case 0x80000008: SET_ABCD(0x00003028, 0x00000000, 0x00000000, 0x00000000); break; default: SET_ABCD(0x00000000, 0x00000000, 0x00000000, 0x00000000); break; }# undef SET_ABCD}ULong amd64g_calculate_RCR ( ULong arg, ULong rot_amt, ULong rflags_in, Long szIN ){ Bool wantRflags = toBool(szIN < 0); ULong sz = wantRflags ? (-szIN) : szIN; ULong tempCOUNT = rot_amt & (sz == 8 ? 0x3F : 0x1F); ULong cf=0, of=0, tempcf; switch (sz) { case 8: cf = (rflags_in >> AMD64G_CC_SHIFT_C) & 1; of = ((arg >> 63) ^ cf) & 1; while (tempCOUNT > 0) { tempcf = arg & 1; arg = (arg >> 1) | (cf << 63); cf = tempcf; tempCOUNT--; } break; case 4: while (tempCOUNT >= 33) tempCOUNT -= 33; cf = (rflags_in >> AMD64G_CC_SHIFT_C) & 1; of = ((arg >> 31) ^ cf) & 1; while (tempCOUNT > 0) { tempcf = arg & 1; arg = ((arg >> 1) & 0x7FFFFFFFULL) | (cf << 31); cf = tempcf; tempCOUNT--; } break; case 2: while (tempCOUNT >= 17) tempCOUNT -= 17; cf = (rflags_in >> AMD64G_CC_SHIFT_C) & 1; of = ((arg >> 15) ^ cf) & 1; while (tempCOUNT > 0) { tempcf = arg & 1; arg = ((arg >> 1) & 0x7FFFULL) | (cf << 15); cf = tempcf; tempCOUNT--; } break; case 1: while (tempCOUNT >= 9) tempCOUNT -= 9; cf = (rflags_in >> AMD64G_CC_SHIFT_C) & 1; of = ((arg >> 7) ^ cf) & 1; while (tempCOUNT > 0) { tempcf = arg & 1; arg = ((arg >> 1) & 0x7FULL) | (cf << 7); cf = tempcf; tempCOUNT--; } break; default: vpanic("calculate_RCR(amd64g): invalid size"); } cf &= 1; of &= 1; rflags_in &= ~(AMD64G_CC_MASK_C | AMD64G_CC_MASK_O); rflags_in |= (cf << AMD64G_CC_SHIFT_C) | (of << AMD64G_CC_SHIFT_O); /* caller can ask to have back either the resulting flags or resulting value, but not both */ return wantRflags ? rflags_in : arg;}/*---------------------------------------------------------------*//*--- Helpers for MMX/SSE/SSE2. ---*//*---------------------------------------------------------------*/static inline UChar abdU8 ( UChar xx, UChar yy ) { return toUChar(xx>yy ? xx-yy : yy-xx);}static inline ULong mk32x2 ( UInt w1, UInt w0 ) { return (((ULong)w1) << 32) | ((ULong)w0);}static inline UShort sel16x4_3 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUShort(hi32 >> 16);}static inline UShort sel16x4_2 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUShort(hi32);}static inline UShort sel16x4_1 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUShort(lo32 >> 16);}static inline UShort sel16x4_0 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUShort(lo32);}static inline UChar sel8x8_7 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUChar(hi32 >> 24);}static inline UChar sel8x8_6 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUChar(hi32 >> 16);}static inline UChar sel8x8_5 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUChar(hi32 >> 8);}static inline UChar sel8x8_4 ( ULong w64 ) { UInt hi32 = toUInt(w64 >> 32); return toUChar(hi32 >> 0);}static inline UChar sel8x8_3 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUChar(lo32 >> 24);}static inline UChar sel8x8_2 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUChar(lo32 >> 16);}static inline UChar sel8x8_1 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUChar(lo32 >> 8);}static inline UChar sel8x8_0 ( ULong w64 ) { UInt lo32 = toUInt(w64); return toUChar(lo32 >> 0);}/* CALLED FROM GENERATED CODE: CLEAN HELPER */ULong amd64g_calculate_mmx_pmaddwd ( ULong xx, ULong yy ){ return mk32x2( (((Int)(Short)sel16x4_3(xx)) * ((Int)(Short)sel16x4_3(yy))) + (((Int)(Short)sel16x4_2(xx)) * ((Int)(Short)sel16x4_2(yy))), (((Int)(Short)sel16x4_1(xx)) * ((Int)(Short)sel16x4_1(yy))) + (((Int)(Short)sel16x4_0(xx)) * ((Int)(Short)sel16x4_0(yy))) );}/* CALLED FROM GENERATED CODE: CLEAN HELPER */ULong amd64g_calculate_mmx_pmovmskb ( ULong xx ){ ULong r = 0; if (xx & (1ULL << (64-1))) r |= (1<<7); if (xx & (1ULL << (56-1))) r |= (1<<6); if (xx & (1ULL << (48-1))) r |= (1<<5); if (xx & (1ULL << (40-1))) r |= (1<<4); if (xx & (1ULL << (32-1))) r |= (1<<3); if (xx & (1ULL << (24-1))) r |= (1<<2); if (xx & (1ULL << (16-1))) r |= (1<<1); if (xx & (1ULL << ( 8-1))) r |= (1<<0); return r;}/* CALLED FROM GENERATED CODE: CLEAN HELPER */ULong amd64g_calculate_mmx_psadbw ( ULong xx, ULong yy ){ UInt t = 0; t += (UInt)abdU8( sel8x8_7(xx), sel8x8_7(yy) ); t += (UInt)abdU8( sel8x8_6(xx), sel8x8_6(yy) ); t += (UInt)abdU8( sel8x8_5(xx), sel8x8_5(yy) ); t += (UInt)abdU8( sel8x8_4(xx), sel8x8_4(yy) ); t += (UInt)abdU8( sel8x8_3(xx), sel8x8_3(yy) ); t += (UInt)abdU8( sel8x8_2(xx), sel8x8_2(yy) ); t += (UInt)abdU8( sel8x8_1(xx), sel8x8_1(yy) ); t += (UInt)abdU8( sel8x8_0(xx), sel8x8_0(yy) ); t &= 0xFFFF; return (ULong)t;}/* CALLED FROM GENERATED CODE: CLEAN HELPER */ULong amd64g_calculate_sse_pmovmskb ( ULong w64hi, ULong w64lo ){ ULong rHi8 = amd64g_calculate_mmx_pmovmskb ( w64hi ); ULong rLo8 = amd64g_calculate_mmx_pmovmskb ( w64lo ); return ((rHi8 & 0xFF) << 8) | (rLo8 & 0xFF);}/*---------------------------------------------------------------*//*--- Helpers for dealing with, and describing, ---*//*--- guest state as a whole. ---*//*---------------------------------------------------------------*//* Initialise the entire amd64 guest state. *//* VISIBLE TO LIBVEX CLIENT */void LibVEX_GuestAMD64_initialise ( /*OUT*/VexGuestAMD64State* vex_state ){ //Int i; vex_state->guest_RAX = 0; vex_state->guest_RCX = 0; vex_state->guest_RDX = 0; vex_state->guest_RBX = 0; vex_state->guest_RSP = 0; vex_state->guest_RBP = 0; vex_state->guest_RSI = 0; vex_state->guest_RDI = 0; vex_state->guest_R8 = 0; vex_state->guest_R9 = 0; vex_state->guest_R10 = 0; vex_state->guest_R11 = 0; vex_state->guest_R12 = 0; vex_state->guest_R13 = 0; vex_state->guest_R14 = 0; vex_state->guest_R15 = 0; vex_state->guest_CC_OP = AMD64G_CC_OP_COPY; vex_state->guest_CC_DEP1 = 0; vex_state->guest_CC_DEP2 = 0; vex_state->guest_CC_NDEP = 0; vex_state->guest_DFLAG = 1; /* forwards */ vex_state->guest_IDFLAG = 0; /* HACK: represent the offset associated with %fs==0. This assumes that %fs is only ever zero. */ vex_state->guest_FS_ZERO = 0; vex_state->guest_RIP = 0; /* Initialise the simulated FPU */ amd64g_dirtyhelper_FINIT( vex_state ); /* Initialise the SSE state. */# define SSEZERO(_xmm) _xmm[0]=_xmm[1]=_xmm[2]=_xmm[3] = 0; vex_state->guest_SSEROUND = (ULong)Irrm_NEAREST; SSEZERO(vex_state->guest_XMM0); SSEZERO(vex_state->guest_XMM1); SSEZERO(vex_state->guest_XMM2); SSEZERO(vex_state->guest_XMM3); SSEZERO(vex_state->guest_XMM4); SSEZERO(vex_state->guest_XMM5)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -