generate a segfault and then restart the instruction.
git-svn-id: svn://svn.valgrind.org/vex/trunk@1786
/* ------------------------ 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;
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 */
}
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 */
/* ------------------------ 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
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:
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:
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:
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;
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' */
#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 */