mirror of
https://github.com/ptitSeb/box64.git
synced 2024-11-26 16:21:17 +00:00
Improved Signal handling ([ARM4_DYNAREC] too)
Some checks are pending
Build and Release Box64 / build (ubuntu-latest, ANDROID, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ANDROID, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, TERMUX, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, TERMUX, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Trace) (push) Waiting to run
Some checks are pending
Build and Release Box64 / build (ubuntu-latest, ANDROID, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ANDROID, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, ARM64, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, LARCH64, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RISCV, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, StaticBuild) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, RK3588, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, TERMUX, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, TERMUX, Trace) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Box32) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Release) (push) Waiting to run
Build and Release Box64 / build (ubuntu-latest, X64, Trace) (push) Waiting to run
This commit is contained in:
parent
4ac43047d0
commit
8f08a14115
@ -1471,7 +1471,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
MOV32w(x1, 0x202);
|
||||
ORRw_REG(xFlags, xFlags, x1);
|
||||
SET_DFNONE(x1);
|
||||
if(box64_wine) { // should this be done all the time?
|
||||
if(box64_wine || 1) { // should this be done all the time?
|
||||
TBZ_NEXT(xFlags, F_TF);
|
||||
// go to epilog, TF should trigger at end of next opcode, so using Interpreter only
|
||||
jump_to_epilog(dyn, addr, 0, ninst);
|
||||
@ -2443,7 +2443,11 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
} else {
|
||||
INST_NAME("INT n");
|
||||
SETFLAGS(X_ALL, SF_SET_NODF); // Hack to set flags in "don't care" state
|
||||
GETIP(ip); // priviledged instruction, IP not updated
|
||||
if(rex.is32bits && u8==0x04) {
|
||||
GETIP(addr);
|
||||
} else {
|
||||
GETIP(ip); // priviledged instruction, IP not updated
|
||||
}
|
||||
STORE_XEMU_CALL(xRIP);
|
||||
MOV32w(x1,u8);
|
||||
CALL(native_int, -1);
|
||||
@ -2462,6 +2466,7 @@ uintptr_t dynarec64_00(dynarec_arm_t* dyn, uintptr_t addr, uintptr_t ip, int nin
|
||||
GETIP(addr);
|
||||
TBZ_NEXT(wFlags, F_OF);
|
||||
STORE_XEMU_CALL(xRIP);
|
||||
MOV32w(x1,4);
|
||||
CALL(native_int, -1);
|
||||
LOAD_XEMU_CALL(xRIP);
|
||||
}
|
||||
|
@ -194,7 +194,7 @@ void native_int3(x64emu_t* emu)
|
||||
void native_div0(x64emu_t* emu)
|
||||
{
|
||||
emu->test.test = 0;
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
}
|
||||
|
||||
void native_fsave(x64emu_t* emu, uint8_t* ed)
|
||||
|
@ -11,8 +11,8 @@
|
||||
#define F64S *(int64_t*)(addr+=8, addr-8)
|
||||
#define PK(a) *(uint8_t*)(addr+a)
|
||||
#ifdef DYNAREC
|
||||
#define STEP check_exec(emu, addr); if(step) return 0;
|
||||
#define STEP2 check_exec(emu, addr); if(step) {R_RIP = addr; return 0;}
|
||||
#define STEP check_exec(emu, addr); if(step && !ACCESS_FLAG(F_TF)) return 0;
|
||||
#define STEP2 check_exec(emu, addr); if(step && !ACCESS_FLAG(F_TF)) {R_RIP = addr; return 0;}
|
||||
#define STEP3 check_exec(emu, addr); if(*step) (*step)++;
|
||||
#else
|
||||
#define STEP
|
||||
@ -110,6 +110,7 @@
|
||||
#define FAKEED32(D) GetEd32O(emu, &addr, rex, nextop, D, 0)
|
||||
#define GETEA(D) GetEA(emu, &addr, rex, nextop, D)
|
||||
#define GETEA32(D) GetEA32(emu, &addr, rex, nextop, D)
|
||||
#define GETEA32_16(D) GetEA32_16(emu, &addr, rex, nextop, D)
|
||||
#define _GETED(D) oped=GetEd(emu, &addr, rex, nextop, D)
|
||||
#define _GETED_OFFS(D, O) oped=GetEdO(emu, &addr, rex, nextop, D, O)
|
||||
#define _GETED32(D) oped=GetEd32O(emu, &addr, rex, nextop, D, 0)
|
||||
|
@ -578,15 +578,15 @@ void UnimpOpcode(x64emu_t* emu, int is32bits)
|
||||
R_RIP = emu->old_ip;
|
||||
|
||||
int tid = syscall(SYS_gettid);
|
||||
printf_log(LOG_NONE, "%04d|%p: Unimplemented %sOpcode (%02X %02X %02X %02X) %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\n",
|
||||
printf_log(LOG_INFO, "%04d|%p: Unimplemented %sOpcode (%02X %02X %02X %02X) %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X %02X\n",
|
||||
tid, (void*)emu->old_ip, is32bits?"32bits ":"",
|
||||
Peek(emu, -4), Peek(emu, -3), Peek(emu, -2), Peek(emu, -1),
|
||||
Peek(emu, 0), Peek(emu, 1), Peek(emu, 2), Peek(emu, 3),
|
||||
Peek(emu, 4), Peek(emu, 5), Peek(emu, 6), Peek(emu, 7),
|
||||
Peek(emu, 8), Peek(emu, 9), Peek(emu,10), Peek(emu,11),
|
||||
Peek(emu,12), Peek(emu,13), Peek(emu,14));
|
||||
emu->quit=1;
|
||||
emu->error |= ERR_UNIMPL;
|
||||
//emu->quit=1;
|
||||
//emu->error |= ERR_UNIMPL;
|
||||
}
|
||||
|
||||
void EmuCall(x64emu_t* emu, uintptr_t addr)
|
||||
|
@ -245,6 +245,8 @@ x64emurun:
|
||||
}
|
||||
emu->segs[_SS] = Pop32(emu); // no check, no use....
|
||||
emu->segs_serial[_SS] = 0;
|
||||
if(ACCESS_FLAG(F_TF))
|
||||
tf_next = 1;
|
||||
break;
|
||||
|
||||
case 0x1E: /* PUSH DS */
|
||||
@ -590,10 +592,8 @@ x64emurun:
|
||||
#ifndef TEST_INTERPRETER
|
||||
if(rex.is32bits && box64_ignoreint3)
|
||||
{
|
||||
F8;
|
||||
} else {
|
||||
F8;
|
||||
emit_signal(emu, SIGSEGV, (void*)R_RIP, 0);
|
||||
emit_signal(emu, SIGSEGV, (void*)R_RIP, 0xbad0);
|
||||
}
|
||||
STEP;
|
||||
#endif
|
||||
@ -826,6 +826,8 @@ x64emurun:
|
||||
GETED(0);
|
||||
emu->segs[((nextop&0x38)>>3)] = ED->word[0];
|
||||
emu->segs_serial[((nextop&0x38)>>3)] = 0;
|
||||
if(((nextop&0x38)>>3)==_SS && ACCESS_FLAG(F_TF))
|
||||
tf_next = 1;
|
||||
break;
|
||||
case 0x8F: /* POP Ed */
|
||||
nextop = F8;
|
||||
@ -1544,6 +1546,8 @@ x64emurun:
|
||||
emit_interruption(emu, 0x29, (void*)R_RIP);
|
||||
} else if (tmp8u==0x80) {
|
||||
R_RIP = addr;
|
||||
if(ACCESS_FLAG(F_TF))
|
||||
tf_next = 1;
|
||||
// 32bits syscall
|
||||
#ifndef TEST_INTERPRETER
|
||||
x86Syscall(emu);
|
||||
@ -1556,6 +1560,9 @@ x64emurun:
|
||||
STEP2;
|
||||
#endif
|
||||
} else {
|
||||
if(rex.is32bits && tmp8u==0x04) {
|
||||
R_RIP = addr;
|
||||
}
|
||||
#ifndef TEST_INTERPRETER
|
||||
emit_interruption(emu, tmp8u, (void*)R_RIP);
|
||||
STEP2;
|
||||
@ -1572,7 +1579,7 @@ x64emurun:
|
||||
#ifndef TEST_INTERPRETER
|
||||
CHECK_FLAGS(emu);
|
||||
if(ACCESS_FLAG(F_OF))
|
||||
emit_signal(emu, SIGSEGV, (void*)R_RIP, 128);
|
||||
emit_interruption(emu, 4, (void*)R_RIP);
|
||||
STEP2;
|
||||
#endif
|
||||
break;
|
||||
@ -1954,12 +1961,12 @@ x64emurun:
|
||||
break;
|
||||
case 6: /* DIV Eb */
|
||||
if(!EB->byte[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
div8(emu, EB->byte[0]);
|
||||
break;
|
||||
case 7: /* IDIV Eb */
|
||||
if(!EB->byte[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
idiv8(emu, EB->byte[0]);
|
||||
break;
|
||||
}
|
||||
@ -1989,12 +1996,12 @@ x64emurun:
|
||||
break;
|
||||
case 6: /* DIV Ed */
|
||||
if(!ED->q[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
div64(emu, ED->q[0]);
|
||||
break;
|
||||
case 7: /* IDIV Ed */
|
||||
if(!ED->q[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
idiv64(emu, ED->q[0]);
|
||||
break;
|
||||
}
|
||||
@ -2029,14 +2036,14 @@ x64emurun:
|
||||
break;
|
||||
case 6: /* DIV Ed */
|
||||
if(!ED->dword[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
div32(emu, ED->dword[0]);
|
||||
//emu->regs[_AX].dword[1] = 0; // already put high regs to 0
|
||||
//emu->regs[_DX].dword[1] = 0;
|
||||
break;
|
||||
case 7: /* IDIV Ed */
|
||||
if(!ED->dword[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
idiv32(emu, ED->dword[0]);
|
||||
//emu->regs[_AX].dword[1] = 0;
|
||||
//emu->regs[_DX].dword[1] = 0;
|
||||
@ -2256,7 +2263,7 @@ if(emu->segs[_CS]!=0x33 && emu->segs[_CS]!=0x23) printf_log(LOG_NONE, "Warning,
|
||||
#ifndef TEST_INTERPRETER
|
||||
printf_log(LOG_DEBUG, "End of X86 run (%p), RIP=%p, Stack=%p, unimp=%d, emu->fork=%d, emu->uc_link=%p, emu->quit=%d\n", emu, (void*)R_RIP, (void*)R_RSP, unimp, emu->fork, emu->uc_link, emu->quit);
|
||||
if(unimp) {
|
||||
emu->quit = 1;
|
||||
//emu->quit = 1;
|
||||
UnimpOpcode(emu, is32bits);
|
||||
emit_signal(emu, SIGILL, (void*)R_RIP, 0);
|
||||
}
|
||||
|
@ -792,12 +792,12 @@ uintptr_t Run64(x64emu_t *emu, rex_t rex, int seg, uintptr_t addr)
|
||||
break;
|
||||
case 6: /* DIV Eb */
|
||||
if(!EB->byte[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
div8(emu, EB->byte[0]);
|
||||
break;
|
||||
case 7: /* IDIV Eb */
|
||||
if(!EB->byte[0])
|
||||
emit_div0(emu, (void*)R_RIP, 0);
|
||||
emit_div0(emu, (void*)R_RIP, 1);
|
||||
idiv8(emu, EB->byte[0]);
|
||||
break;
|
||||
}
|
||||
|
@ -66,6 +66,21 @@ uintptr_t Run67_32(x64emu_t *emu, rex_t rex, int rep, uintptr_t addr)
|
||||
return Run6764_32(emu, rex, rep, _GS, addr);
|
||||
#endif
|
||||
break;
|
||||
case 0x66:
|
||||
opcode = F8;
|
||||
switch(opcode) {
|
||||
|
||||
case 0x8D: /* LEA Gw,M */
|
||||
nextop = F8;
|
||||
GETGW;
|
||||
tmp32u = GETEA32_16(0);
|
||||
GW->word[0] = (uint16_t)tmp32u;
|
||||
break;
|
||||
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xE0: /* LOOPNZ */
|
||||
CHECK_FLAGS(emu);
|
||||
|
@ -1701,6 +1701,14 @@ uintptr_t GetEA32(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t
|
||||
} else return (uintptr_t)GetECommon32O(emu, addr, rex, m, delta, 0);
|
||||
}
|
||||
|
||||
uintptr_t GetEA32_16(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta)
|
||||
{
|
||||
uint8_t m = v&0xC7; // filter Ed
|
||||
if(m>=0xC0) {
|
||||
return (uintptr_t)&emu->regs[(m&0x07)+(rex.b<<3)];
|
||||
} else return (uintptr_t)GetEw16off(emu, addr, rex, m, delta);
|
||||
}
|
||||
|
||||
reg64_t* GetEdO(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset)
|
||||
{
|
||||
uint8_t m = v&0xC7; // filter Ed
|
||||
|
@ -115,6 +115,7 @@ static inline void PushExit_32(x64emu_t* emu)
|
||||
reg64_t* GetECommon(x64emu_t* emu, uintptr_t* addr, rex_t rex, uint8_t m, uint8_t delta);
|
||||
reg64_t* GetECommonO(x64emu_t* emu, uintptr_t* addr, rex_t rex, uint8_t m, uint8_t delta, uintptr_t offset);
|
||||
reg64_t* GetECommon32O(x64emu_t* emu, uintptr_t* addr, rex_t rex, uint8_t m, uint8_t delta, uintptr_t offset);
|
||||
reg64_t* GetECommon32O_16(x64emu_t* emu, uintptr_t* addr, rex_t rex, uint8_t m, uint8_t delta, uintptr_t offset);
|
||||
reg64_t* GetEb(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
reg64_t* TestEb(x64test_t *test, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
reg64_t* GetEbO(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset);
|
||||
@ -129,6 +130,7 @@ reg64_t* TestEd8xw(x64test_t *test, int w, uintptr_t* addr, rex_t rex, uint8_t v
|
||||
reg64_t* TestEdt(x64test_t *test, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
uintptr_t GetEA(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
uintptr_t GetEA32(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
uintptr_t GetEA32_16(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta);
|
||||
reg64_t* GetEdO(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset);
|
||||
reg64_t* TestEdO(x64test_t *test, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset);
|
||||
reg64_t* GetEd32O(x64emu_t *emu, uintptr_t* addr, rex_t rex, uint8_t v, uint8_t delta, uintptr_t offset);
|
||||
|
@ -250,6 +250,61 @@ struct kernel_sigaction {
|
||||
unsigned long sa_mask;
|
||||
unsigned long sa_mask2;
|
||||
};
|
||||
|
||||
typedef struct __attribute__((packed, aligned(4))) my_siginfo32_s
|
||||
{
|
||||
int si_signo;
|
||||
int si_errno;
|
||||
int si_code;
|
||||
union {
|
||||
int _pad[128/sizeof(int)-3];
|
||||
struct {
|
||||
__pid_t __si_pid;
|
||||
__uid_t __si_uid;
|
||||
} _kill;
|
||||
struct {
|
||||
int si_tid;
|
||||
int __si_overrun;
|
||||
__sigval_t si_sigval;
|
||||
} _timer;
|
||||
struct {
|
||||
__pid_t __si_pid;
|
||||
__uid_t __si_uid;
|
||||
__sigval_t si_sigval;
|
||||
} _rt;
|
||||
struct {
|
||||
__pid_t __si_pid;
|
||||
__uid_t __si_uid;
|
||||
int __si_status;
|
||||
__clock_t __si_utime;
|
||||
__clock_t __si_stime;
|
||||
} _sigchld;
|
||||
struct {
|
||||
ptr_t __si_addr;
|
||||
__SI_SIGFAULT_ADDL
|
||||
short int __si_addr_lsb;
|
||||
union {
|
||||
struct {
|
||||
ptr_t _lower;
|
||||
ptr_t _upper;
|
||||
} _addr_bnd;
|
||||
__uint32_t _pkey;
|
||||
} _bounds;
|
||||
} _sigfault;
|
||||
struct
|
||||
{
|
||||
long int __si_band;
|
||||
int __si_fd;
|
||||
} _sigpoll;
|
||||
struct
|
||||
{
|
||||
ptr_t _call_addr;
|
||||
int _syscall;
|
||||
unsigned int _arch;
|
||||
} _sigsys;
|
||||
} _sifields;
|
||||
} my_siginfo32_t;
|
||||
|
||||
#ifdef DYNAREC
|
||||
uintptr_t getX64Address(dynablock_t* db, uintptr_t arm_addr);
|
||||
#endif
|
||||
@ -400,7 +455,7 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
int Locks = unlockMutex();
|
||||
int log_minimum = (box64_showsegv)?LOG_NONE:((sig==SIGSEGV && my_context->is_sigaction[sig])?LOG_DEBUG:LOG_INFO);
|
||||
|
||||
printf_log(LOG_DEBUG, "Sigactionhanlder for signal #%d called (jump to %p/%s)\n", sig, (void*)my_context->signals[sig], GetNativeName((void*)my_context->signals[sig]));
|
||||
printf_log(LOG_INFO/*LOG_DEBUG*/, "Sigactionhanlder32 for signal #%d called (jump to %p/%s)\n", sig, (void*)my_context->signals[sig], GetNativeName((void*)my_context->signals[sig]));
|
||||
|
||||
uintptr_t restorer = my_context->restorer[sig];
|
||||
// get that actual ESP first!
|
||||
@ -462,9 +517,11 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
// setup stack frame
|
||||
frame -= 512+64+16*16;
|
||||
void* xstate = (void*)frame;
|
||||
frame -= sizeof(siginfo_t);
|
||||
siginfo_t* info2 = (siginfo_t*)frame;
|
||||
memcpy(info2, info, sizeof(siginfo_t));
|
||||
frame -= sizeof(my_siginfo32_t);
|
||||
my_siginfo32_t* info2 = (my_siginfo32_t*)frame;
|
||||
memcpy(info2, info, sizeof(my_siginfo32_t));
|
||||
if(sig==SIGILL || sig==SIGFPE || sig==SIGSEGV || sig==SIGBUS)
|
||||
info2->_sifields._sigfault.__si_addr = to_ptrv(info->si_addr);
|
||||
// try to fill some sigcontext....
|
||||
frame -= sizeof(i386_ucontext_t);
|
||||
i386_ucontext_t *sigcontext = (i386_ucontext_t*)frame;
|
||||
@ -580,7 +637,9 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
//bad opcode
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0;
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 13;
|
||||
info2->si_code = 128;
|
||||
info2->si_errno = 0;
|
||||
info2->_sifields._sigfault.__si_addr = 0;
|
||||
} else if (info->si_errno==0xecec) {
|
||||
// no excute bit on segment
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 16;//(real_prot&PROT_READ)?16:1; // EXECUTE_FAULT & READ_FAULT
|
||||
@ -598,7 +657,7 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
if((info->si_code!=SEGV_ACCERR) && labs((intptr_t)info->si_addr-(intptr_t)sigcontext->uc_mcontext.gregs[I386_ESP])<16)
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 12; // stack overflow probably
|
||||
else
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = (info->si_code == SEGV_ACCERR)?14:13;
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = (mmapped || ((uintptr_t)info->si_addr<0x10000))?14:13;
|
||||
//I386_ERR seems to be INT:8 CODE:8. So for write access segfault it's 0x0002 For a read it's 0x0004 (and 8 for exec). For an int 2d it could be 0x2D01 for example
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0x0001; // read error?
|
||||
}
|
||||
@ -610,8 +669,8 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
// INT x
|
||||
uint8_t int_n = info->si_code;
|
||||
info2->si_errno = 0;
|
||||
info2->si_code = info->si_code;
|
||||
info2->si_addr = NULL;
|
||||
info2->si_code = 128;
|
||||
info2->_sifields._sigfault.__si_addr = 0;
|
||||
// some special cases...
|
||||
if(int_n==3) {
|
||||
info2->si_signo = SIGTRAP;
|
||||
@ -624,9 +683,11 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0x02|(int_n<<3);
|
||||
} else {
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0x0a|(int_n<<3);
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 13;
|
||||
}
|
||||
} else if(info->si_errno==0xcafe) {
|
||||
} else if(info->si_errno==0xcafe) { //divide by 0
|
||||
info2->si_errno = 0;
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0;
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 0;
|
||||
info2->si_signo = SIGFPE;
|
||||
}
|
||||
@ -635,15 +696,20 @@ void my_sigactionhandler_oldcode_32(int32_t sig, int simple, siginfo_t* info, vo
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 4;
|
||||
else
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 19;
|
||||
} else if(sig==SIGILL)
|
||||
} else if(sig==SIGILL) {
|
||||
info2->si_code = 2;
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = 6;
|
||||
else if(sig==SIGTRAP) {
|
||||
info2->si_code = 128;
|
||||
} else if(sig==SIGTRAP) {
|
||||
if(info->si_code==1) { //single step
|
||||
info2->si_code = 2;
|
||||
info2->_sifields._sigfault.__si_addr = sigcontext->uc_mcontext.gregs[I386_EIP];
|
||||
} else
|
||||
info2->si_code = 128;
|
||||
sigcontext->uc_mcontext.gregs[I386_TRAPNO] = info->si_code;
|
||||
sigcontext->uc_mcontext.gregs[I386_ERR] = 0;
|
||||
}
|
||||
//TODO: SIGABRT generate what?
|
||||
printf_log((sig==10)?LOG_DEBUG:log_minimum, "Signal %d: si_addr=%p, TRAPNO=%d, ERR=%d, RIP=%p, prot:%x, mmaped:%d\n", sig, (void*)info2->si_addr, sigcontext->uc_mcontext.gregs[I386_TRAPNO], sigcontext->uc_mcontext.gregs[I386_ERR],from_ptrv(sigcontext->uc_mcontext.gregs[I386_EIP]), prot, mmapped);
|
||||
printf_log((sig==10)?LOG_DEBUG:log_minimum, "Signal32 %d: si_addr=%p, TRAPNO=%d, ERR=%d, RIP=%p, prot:%x, mmaped:%d\n", sig, from_ptrv(info2->_sifields._sigfault.__si_addr), sigcontext->uc_mcontext.gregs[I386_TRAPNO], sigcontext->uc_mcontext.gregs[I386_ERR],from_ptrv(sigcontext->uc_mcontext.gregs[I386_EIP]), prot, mmapped);
|
||||
// call the signal handler
|
||||
i386_ucontext_t sigcontext_copy = *sigcontext;
|
||||
// save old value from emu
|
||||
|
@ -1161,14 +1161,16 @@ void my_sigactionhandler_oldcode(x64emu_t* emu, int32_t sig, int simple, siginfo
|
||||
//bad opcode
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0;
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 13;
|
||||
info2->si_code = 128;
|
||||
info2->si_errno = 0;
|
||||
info2->si_addr = NULL;
|
||||
} else if (info->si_errno==0xecec) {
|
||||
// no excute bit on segment
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 16;//(real_prot&PROT_READ)?16:1; // EXECUTE_FAULT & READ_FAULT
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = (real_prot&PROT_READ)?16:1; // EXECUTE_FAULT & READ_FAULT
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = mmapped?14:13;
|
||||
info2->si_errno = 0;
|
||||
}else {
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = mmapped?16:1;//(real_prot&PROT_READ)?16:1;//(info->si_errno==0x1234)?0:((info->si_errno==0xdead)?(0x2|(info->si_code<<3)):0x0010); // execution flag issue (probably), unless it's a #GP(0)
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = (real_prot&PROT_READ)?16:1;//(info->si_errno==0x1234)?0:((info->si_errno==0xdead)?(0x2|(info->si_code<<3)):0x0010); // execution flag issue (probably), unless it's a #GP(0)
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = mmapped?14:13;
|
||||
//sigcontext->uc_mcontext.gregs[X64_TRAPNO] = ((info->si_code==SEGV_ACCERR) || (info->si_errno==0x1234) || (info->si_errno==0xdead) || ((uintptr_t)info->si_addr==0))?13:14;
|
||||
}
|
||||
@ -1179,7 +1181,7 @@ void my_sigactionhandler_oldcode(x64emu_t* emu, int32_t sig, int simple, siginfo
|
||||
if((info->si_code!=SEGV_ACCERR) && labs((intptr_t)info->si_addr-(intptr_t)sigcontext->uc_mcontext.gregs[X64_RSP])<16)
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 12; // stack overflow probably
|
||||
else
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = (info->si_code == SEGV_ACCERR)?14:13;
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = mmapped?14:13;
|
||||
//X64_ERR seems to be INT:8 CODE:8. So for write access segfault it's 0x0002 For a read it's 0x0004 (and 8 for exec). For an int 2d it could be 0x2D01 for example
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0x0001; // read error?
|
||||
}
|
||||
@ -1191,7 +1193,7 @@ void my_sigactionhandler_oldcode(x64emu_t* emu, int32_t sig, int simple, siginfo
|
||||
// INT x
|
||||
uint8_t int_n = info->si_code;
|
||||
info2->si_errno = 0;
|
||||
info2->si_code = info->si_code;
|
||||
info2->si_code = 128;
|
||||
info2->si_addr = NULL;
|
||||
// some special cases...
|
||||
if(int_n==3) {
|
||||
@ -1205,9 +1207,11 @@ void my_sigactionhandler_oldcode(x64emu_t* emu, int32_t sig, int simple, siginfo
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0x02|(int_n<<3);
|
||||
} else {
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0x0a|(int_n<<3);
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 13;
|
||||
}
|
||||
} else if(info->si_errno==0xcafe) {
|
||||
} else if(info->si_errno==0xcafe) { // divide by 0
|
||||
info2->si_errno = 0;
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0;
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 0;
|
||||
info2->si_signo = SIGFPE;
|
||||
}
|
||||
@ -1216,10 +1220,15 @@ void my_sigactionhandler_oldcode(x64emu_t* emu, int32_t sig, int simple, siginfo
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 4;
|
||||
else
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 19;
|
||||
} else if(sig==SIGILL)
|
||||
} else if(sig==SIGILL) {
|
||||
info2->si_code = 2;
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = 6;
|
||||
else if(sig==SIGTRAP) {
|
||||
info2->si_code = 128;
|
||||
} else if(sig==SIGTRAP) {
|
||||
if(info->si_code==1) { //single step
|
||||
info2->si_code = 2;
|
||||
info2->si_addr = (void*)sigcontext->uc_mcontext.gregs[X64_RIP];
|
||||
} else
|
||||
info2->si_code = 128;
|
||||
sigcontext->uc_mcontext.gregs[X64_TRAPNO] = info->si_code;
|
||||
sigcontext->uc_mcontext.gregs[X64_ERR] = 0;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user