diff --git a/debugger/shell.d b/debugger/shell.d index b81c8c11..88f2889e 100644 --- a/debugger/shell.d +++ b/debugger/shell.d @@ -636,48 +636,54 @@ void shell_event_disassemble(size_t address, int count = 1, bool showAddress = t } } -void shell_event_exception(adbg_process_t *proc, int event, void* evdata) { - if (event != AdbgEvent.exception) - return; - - adbg_exception_t *ex = cast(adbg_exception_t*)evdata; - - printf("* Process %d (thread %d) stopped\n"~ - " Reason : %s ("~ADBG_OS_ERROR_FORMAT~")\n", - ex.pid, ex.tid, - adbg_exception_name(ex), ex.oscode); - - if (ex.faultz) { +void shell_event_exception(adbg_process_t *proc, int event, void *edata, void *udata) { + switch (event) with (AdbgEvent) { + case exception: + adbg_exception_t *ex = cast(adbg_exception_t*)edata; + + printf("* Process %d (thread %d) stopped\n"~ + " Reason : %s ("~ADBG_OS_ERROR_FORMAT~")\n", + ex.pid, ex.tid, + adbg_exception_name(ex), ex.oscode); + + // No fault address available + if (ex.faultz == 0) + return; + printf(" Address : 0x%llx\n", ex.fault_address); - if (dis) { - printf(" Machine :"); - - // Print machine bytes - ubyte[MAX_INSTR_SIZE] data = void; - if (adbg_memory_read(process, ex.faultz, data.ptr, MAX_INSTR_SIZE)) { - printf(" read error (%s)\n", adbg_error_message()); - return; // Nothing else to do - } - - adbg_opcode_t op = void; - if (adbg_dis_once(dis, &op, data.ptr, MAX_INSTR_SIZE)) { - printf(" disassembly error (%s)\n", adbg_error_message()); - return; - } - - // Print machine bytes - for (size_t bi; bi < op.size; ++bi) { - printf(" %02x", op.machine[bi]); - } - putchar('\n'); - - // Print mnemonic - printf(" Mnemonic: %s", op.mnemonic); - if (op.operands) - printf(" %s", op.operands); - putchar('\n'); + // No disassembler available + if (dis == null) + return; + + printf(" Machine :"); + + // Print machine bytes + ubyte[MAX_INSTR_SIZE] data = void; + if (adbg_memory_read(process, ex.faultz, data.ptr, MAX_INSTR_SIZE)) { + printf(" read error (%s)\n", adbg_error_message()); + return; // Nothing else to do + } + + adbg_opcode_t op = void; + if (adbg_dis_once(dis, &op, data.ptr, MAX_INSTR_SIZE)) { + printf(" disassembly error (%s)\n", adbg_error_message()); + return; + } + + // Print machine bytes + for (size_t bi; bi < op.size; ++bi) { + printf(" %02x", op.machine[bi]); } + putchar('\n'); + + // Print mnemonic + printf(" Mnemonic: %s", op.mnemonic); + if (op.operands) + printf(" %s", op.operands); + putchar('\n'); + return; + default: } } @@ -824,7 +830,7 @@ int command_restart(int argc, const(char) **argv) { int command_go(int argc, const(char) **argv) { if (adbg_debugger_continue(process)) return ShellError.alicedbg; - if (adbg_debugger_wait(process, &shell_event_exception)) + if (adbg_debugger_wait(process, &shell_event_exception, null)) return ShellError.alicedbg; // Temporary: Cheap hack for process exit if (adbg_process_status(process) == AdbgProcStatus.unloaded) @@ -845,7 +851,7 @@ int command_kill(int argc, const(char) **argv) { int command_stepi(int argc, const(char) **argv) { if (adbg_debugger_stepi(process)) return ShellError.alicedbg; - if (adbg_debugger_wait(process, &shell_event_exception)) + if (adbg_debugger_wait(process, &shell_event_exception, null)) return ShellError.alicedbg; return 0; } diff --git a/examples/simple.d b/examples/simple.d index 0a06459c..1f195bbe 100644 --- a/examples/simple.d +++ b/examples/simple.d @@ -29,11 +29,11 @@ LINPUT: int c = getchar; goto LINPUT; } -void loop_handler(adbg_process_t *proc, int event, void *evdata) { +void loop_handler(adbg_process_t *proc, int event, void *edata, void *udata) { if (event != AdbgEvent.exception) return; - adbg_exception_t *ex = cast(adbg_exception_t*)evdata; + adbg_exception_t *ex = cast(adbg_exception_t*)edata; printf( "\n----------------------------------------\n"~ "* EXCEPTION ("~ADBG_OS_ERROR_FORMAT~"): %s\n"~ @@ -44,18 +44,20 @@ void loop_handler(adbg_process_t *proc, int event, void *evdata) { ex.fault_address ); - // Print disassembly if available - if (dis && ex.faultz) { - adbg_opcode_t op = void; - if (adbg_dis_process_once(dis, &op, proc, ex.fault_address)) { - printf(" (error:%s)\n", adbg_error_message); - return; - } - if (op.operands) - printf(" (%s %s)\n", op.mnemonic, op.operands); - else - printf(" (%s)\n", op.mnemonic); + // If disassembler and fault address unavailable, + // skip printing disassembly + if (dis == null || ex.faultz == 0) + return; + + adbg_opcode_t op = void; + if (adbg_dis_process_once(dis, &op, proc, ex.fault_address)) { + printf(" (error:%s)\n", adbg_error_message); + return; } + if (op.operands) + printf(" (%s %s)\n", op.mnemonic, op.operands); + else + printf(" (%s)\n", op.mnemonic); } int main(int argc, const(char) **argv) { diff --git a/src/adbg/debugger.d b/src/adbg/debugger.d index 3a7effee..ec236b5e 100644 --- a/src/adbg/debugger.d +++ b/src/adbg/debugger.d @@ -239,12 +239,11 @@ version (Windows) { // Introduced in Windows 10, version 1511 // IsWow64Process: 32-bit proc. under aarch64 returns FALSE // NOTE: Could be moved to adbg_process_get_machine - version (Win64) { - if (IsWow64Process(proc.hpid, &proc.wow64) == FALSE) { - adbg_process_free(proc); - adbg_oops(AdbgError.os); - return null; - } + version (Win64) + if (IsWow64Process(proc.hpid, &proc.wow64) == FALSE) { + adbg_process_free(proc); + adbg_oops(AdbgError.os); + return null; } proc.status = AdbgProcStatus.standby; @@ -608,9 +607,11 @@ version (Windows) { /// Params: /// tracee = Tracee instance. /// userfunc = User function callback on event. +/// udata = User data passed to callback. Can be used to identify requests, for example. /// Returns: Error code. int adbg_debugger_wait(adbg_process_t *tracee, - void function(adbg_process_t*, int, void*) userfunc) { + void function(adbg_process_t *proc, int type, void *data, void *user) userfunc, + void *udata) { if (tracee == null || userfunc == null) return adbg_oops(AdbgError.invalidArgument); if (tracee.creation == AdbgCreation.unloaded) @@ -761,7 +762,7 @@ Lwait: adbg_exception_translate(&exception, &tracee.pid, &stopsig); } - userfunc(tracee, AdbgEvent.exception, &exception); + userfunc(tracee, AdbgEvent.exception, &exception, udata); return 0; Lexited: @@ -785,7 +786,7 @@ int adbg_debugger_terminate(adbg_process_t *tracee) { tracee.creation = AdbgCreation.unloaded; scope(exit) { version (Windows) if (tracee.args) free(tracee.args); - //version (Posix) if (tracee.argv) close(tracee.argv); + version (Posix) if (tracee.argv) close(tracee.argv); free(tracee); }