diff --git a/src/linux/demon/linux_demon.c b/src/linux/demon/linux_demon.c index 9c7037a0..e7e202ad 100644 --- a/src/linux/demon/linux_demon.c +++ b/src/linux/demon/linux_demon.c @@ -1792,6 +1792,7 @@ dmn_ctrl_run(Arena *arena, DMN_CtrlCtx *ctx, DMN_RunCtrls *ctrls) // wifexited -> normal process exit via _exit or exit() // wifsignaled -> exit because child did not handle a signal // + B32 is_exception = 0; if(!signal_handled && (wifexited || wifsignaled)) { thread_done = 1; @@ -2291,15 +2292,32 @@ dmn_ctrl_run(Arena *arena, DMN_CtrlCtx *ctx, DMN_RunCtrls *ctrls) // else { + is_exception = 1; + + // rjf: unpack ip + U64 exception_ip = lnx_dmn_ip_from_thread(thread); + + // rjf: pass this signal back thread->pass_through_signal = 1; thread->pass_through_signo = wstopsig; + + // rjf: determine if this is a repeat + B32 is_second_chance = (thread->last_exception_ip == exception_ip && + thread->last_exception_signo == wstopsig); + + // rjf: store this last exception info + thread->last_exception_ip = exception_ip; + thread->last_exception_signo = wstopsig; + + // rjf: report as exception DMN_Event *e = dmn_event_list_push(arena, &events); e->kind = DMN_EventKind_Exception; e->process = lnx_dmn_handle_from_process(thread->process); e->thread = lnx_dmn_handle_from_thread(thread); - e->instruction_pointer = lnx_dmn_ip_from_thread(thread); - e->address = e->instruction_pointer; + e->instruction_pointer = exception_ip; + e->address = exception_ip; e->code = wstopsig; + e->exception_repeated = is_second_chance; if(wstopsig == SIGSEGV) { siginfo_t si = {0}; @@ -2309,6 +2327,15 @@ dmn_ctrl_run(Arena *arena, DMN_CtrlCtx *ctx, DMN_RunCtrls *ctrls) } } + ////////////////////////// + //- rjf: not exception? -> clear this thread's last exception info + // + if(!is_exception && thread != 0) + { + thread->last_exception_ip = 0; + thread->last_exception_signo = 0; + } + ////////////////////////// //- rjf: signal not handled -> log // diff --git a/src/linux/demon/linux_demon.h b/src/linux/demon/linux_demon.h index 22ff00fb..ed6a62a3 100644 --- a/src/linux/demon/linux_demon.h +++ b/src/linux/demon/linux_demon.h @@ -179,6 +179,8 @@ struct LNX_DMN_Thread B32 is_reg_block_dirty; B32 pass_through_signal; B32 ghost_trap; + U64 last_exception_ip; + U64 last_exception_signo; U64 last_name_hash; U64 name_gather_time_us; U64 pass_through_signo;