|
From: <sv...@va...> - 2007-08-29 09:09:20
|
Author: sewardj
Date: 2007-08-29 10:09:17 +0100 (Wed, 29 Aug 2007)
New Revision: 1786
Log:
Support x86 $int 0x40 .. 0x43 instructions on Linux. Apparently these
generate a segfault and then restart the instruction.
Modified:
trunk/priv/guest-amd64/toIR.c
trunk/priv/guest-ppc/toIR.c
trunk/priv/guest-x86/toIR.c
trunk/priv/host-amd64/hdefs.c
trunk/priv/host-ppc/hdefs.c
trunk/priv/host-x86/hdefs.c
trunk/priv/ir/irdefs.c
trunk/pub/libvex_ir.h
trunk/pub/libvex_trc_values.h
Modified: trunk/priv/guest-amd64/toIR.c
===================================================================
--- trunk/priv/guest-amd64/toIR.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/guest-amd64/toIR.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -12446,7 +12446,7 @@
/* ------------------------ INT ------------------------ */
case 0xCC: /* INT 3 */
- jmp_lit(Ijk_Trap, guest_RIP_bbstart + delta);
+ jmp_lit(Ijk_SigTRAP, guest_RIP_bbstart + delta);
dres.whatNext = Dis_StopHere;
DIP("int $0x3\n");
break;
Modified: trunk/priv/guest-ppc/toIR.c
===================================================================
--- trunk/priv/guest-ppc/toIR.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/guest-ppc/toIR.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -4586,7 +4586,7 @@
testing the arguments. */
stmt( IRStmt_Exit(
binop(opCMPEQ, const0, const0),
- Ijk_Trap,
+ Ijk_SigTRAP,
mode64 ? IRConst_U64(cia) : IRConst_U32((UInt)cia)
));
return True; /* unconditional trap */
@@ -4629,7 +4629,7 @@
}
stmt( IRStmt_Exit(
binop(opCMPNE, cond, const0),
- Ijk_Trap,
+ Ijk_SigTRAP,
mode64 ? IRConst_U64(cia) : IRConst_U32((UInt)cia)
));
return False; /* not an unconditional trap */
Modified: trunk/priv/guest-x86/toIR.c
===================================================================
--- trunk/priv/guest-x86/toIR.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/guest-x86/toIR.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -11232,13 +11232,26 @@
/* ------------------------ INT ------------------------ */
case 0xCC: /* INT 3 */
- jmp_lit(Ijk_Trap,((Addr32)guest_EIP_bbstart)+delta);
+ jmp_lit(Ijk_SigTRAP,((Addr32)guest_EIP_bbstart)+delta);
dres.whatNext = Dis_StopHere;
DIP("int $0x3\n");
break;
case 0xCD: /* INT imm8 */
d32 = getIByte(delta); delta++;
+
+ /* Handle int $0x40 .. $0x43 by synthesising a segfault and a
+ restart of this instruction (hence the "-2" two lines below,
+ to get the restart EIP to be this instruction. This is
+ probably Linux-specific and it would be more correct to only
+ do this if the VexAbiInfo says that is what we should do. */
+ if (d32 >= 0x40 && d32 <= 0x43) {
+ jmp_lit(Ijk_SigSEGV,((Addr32)guest_EIP_bbstart)+delta-2);
+ dres.whatNext = Dis_StopHere;
+ DIP("int $0x%x\n", (Int)d32);
+ break;
+ }
+
if (d32 != 0x80) goto decode_failure;
/* It's important that all ArchRegs carry their up-to-date value
at this point. So we declare an end-of-block here, which
Modified: trunk/priv/host-amd64/hdefs.c
===================================================================
--- trunk/priv/host-amd64/hdefs.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/host-amd64/hdefs.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -2689,9 +2689,9 @@
case Ijk_NoRedir:
*p++ = 0xBD;
p = emit32(p, VEX_TRC_JMP_NOREDIR); break;
- case Ijk_Trap:
+ case Ijk_SigTRAP:
*p++ = 0xBD;
- p = emit32(p, VEX_TRC_JMP_TRAP); break;
+ p = emit32(p, VEX_TRC_JMP_SIGTRAP); break;
case Ijk_Ret:
case Ijk_Call:
case Ijk_Boring:
Modified: trunk/priv/host-ppc/hdefs.c
===================================================================
--- trunk/priv/host-ppc/hdefs.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/host-ppc/hdefs.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -2949,7 +2949,7 @@
case Ijk_NoDecode: trc = VEX_TRC_JMP_NODECODE; break;
case Ijk_TInval: trc = VEX_TRC_JMP_TINVAL; break;
case Ijk_NoRedir: trc = VEX_TRC_JMP_NOREDIR; break;
- case Ijk_Trap: trc = VEX_TRC_JMP_TRAP; break;
+ case Ijk_SigTRAP: trc = VEX_TRC_JMP_SIGTRAP; break;
case Ijk_Ret:
case Ijk_Call:
case Ijk_Boring:
Modified: trunk/priv/host-x86/hdefs.c
===================================================================
--- trunk/priv/host-x86/hdefs.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/host-x86/hdefs.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -2297,9 +2297,12 @@
case Ijk_Sys_sysenter:
*p++ = 0xBD;
p = emit32(p, VEX_TRC_JMP_SYS_SYSENTER); break;
- case Ijk_Trap:
+ case Ijk_SigTRAP:
*p++ = 0xBD;
- p = emit32(p, VEX_TRC_JMP_TRAP); break;
+ p = emit32(p, VEX_TRC_JMP_SIGTRAP); break;
+ case Ijk_SigSEGV:
+ *p++ = 0xBD;
+ p = emit32(p, VEX_TRC_JMP_SIGSEGV); break;
case Ijk_Ret:
case Ijk_Call:
case Ijk_Boring:
Modified: trunk/priv/ir/irdefs.c
===================================================================
--- trunk/priv/ir/irdefs.c 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/priv/ir/irdefs.c 2007-08-29 09:09:17 UTC (rev 1786)
@@ -726,7 +726,8 @@
case Ijk_MapFail: vex_printf("MapFail"); break;
case Ijk_TInval: vex_printf("Invalidate"); break;
case Ijk_NoRedir: vex_printf("NoRedir"); break;
- case Ijk_Trap: vex_printf("Trap"); break;
+ case Ijk_SigTRAP: vex_printf("SigTRAP"); break;
+ case Ijk_SigSEGV: vex_printf("SigSEGV"); break;
case Ijk_Sys_syscall: vex_printf("Sys_syscall"); break;
case Ijk_Sys_int32: vex_printf("Sys_int32"); break;
case Ijk_Sys_int128: vex_printf("Sys_int128"); break;
Modified: trunk/pub/libvex_ir.h
===================================================================
--- trunk/pub/libvex_ir.h 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/pub/libvex_ir.h 2007-08-29 09:09:17 UTC (rev 1786)
@@ -1192,7 +1192,8 @@
Ijk_MapFail, /* Vex-provided address translation failed */
Ijk_TInval, /* Invalidate translations before continuing. */
Ijk_NoRedir, /* Jump to un-redirected guest addr */
- Ijk_Trap, /* current instruction did a user trap */
+ Ijk_SigTRAP, /* current instruction synths SIGTRAP */
+ Ijk_SigSEGV, /* current instruction synths SIGSEGV */
/* Unfortunately, various guest-dependent syscall kinds. They
all mean: do a syscall before continuing. */
Ijk_Sys_syscall, /* amd64 'syscall', ppc 'sc' */
Modified: trunk/pub/libvex_trc_values.h
===================================================================
--- trunk/pub/libvex_trc_values.h 2007-08-28 16:39:52 UTC (rev 1785)
+++ trunk/pub/libvex_trc_values.h 2007-08-29 09:09:17 UTC (rev 1786)
@@ -62,8 +62,10 @@
#define VEX_TRC_JMP_TINVAL 61 /* invalidate translations before
continuing */
#define VEX_TRC_JMP_NOREDIR 81 /* jump to undirected guest addr */
-#define VEX_TRC_JMP_TRAP 85 /* deliver trap (SIGTRAP?) before
+#define VEX_TRC_JMP_SIGTRAP 85 /* deliver trap (SIGTRAP) before
continuing */
+#define VEX_TRC_JMP_SIGSEGV 87 /* deliver segv (SIGSEGV) before
+ continuing */
#define VEX_TRC_JMP_EMWARN 63 /* deliver emulation warning before
continuing */
#define VEX_TRC_JMP_EMFAIL 83 /* emulation fatal error; abort system */
|
|
From: Oswald B. <os...@kd...> - 2007-08-29 10:10:35
|
On Wed, Aug 29, 2007 at 10:09:19AM +0100, sv...@va... wrote: > Support x86 $int 0x40 .. 0x43 instructions on Linux. Apparently these > generate a segfault and then restart the instruction. > i think *any* int number except 3, 4 and 0x80 will SEGV - these are the only ones registered with set_system_gate/set_system_intr_gate, i.e. initialized and callable from ring3. -- Hi! I'm a .signature virus! Copy me into your ~/.signature, please! -- Chaos, panic, and disorder - my work here is done. |