8 #define CONTEXT_ARM 0x00200000L
11 #define CONTEXT_ARM64 0x00400000L
14 #define CONTEXT_AMD64 0x00100000L
17 #define CONTEXT_i386 0x00010000L
19 #ifndef IMAGE_FILE_MACHINE_ARM64
20 #define IMAGE_FILE_MACHINE_ARM64 0xAA64
22 #ifndef DEBUG_DUMP_ACTIVE
23 #define DEBUG_DUMP_ACTIVE 1030
27 #define THISCALL(dbginterface, function, ...) dbginterface->lpVtbl->function(dbginterface, __VA_ARGS__)
28 #define ITHISCALL(dbginterface, function, ...) THISCALL(idbg->dbginterface, function, __VA_ARGS__)
48 ULONG Class, Qualifier;
49 if (SUCCEEDED(
ITHISCALL(dbgCtrl, GetDebuggeeType, &Class, &Qualifier))) {
50 if (Class == DEBUG_CLASS_KERNEL) {
76 return SUCCEEDED(
ITHISCALL(dbgCtrl, SetExecutionStatus, DEBUG_STATUS_STEP_INTO));
83 ULONG thread_id = tid;
85 ITHISCALL(dbgSysObj, GetProcessIdBySystemId,
pid, &process_id);
86 ITHISCALL(dbgSysObj, GetThreadIdBySystemId, tid, &thread_id);
88 if (SUCCEEDED(
ITHISCALL(dbgSysObj, SetCurrentProcessId, process_id))) {
89 if (SUCCEEDED(
ITHISCALL(dbgSysObj, SetCurrentThreadId, thread_id))) {
100 ITHISCALL(dbgCtrl, SetExecutionStatus, DEBUG_STATUS_GO);
106 switch (ExceptionCode) {
134 return SUCCEEDED(
ITHISCALL(dbgCtrl, SetInterrupt, DEBUG_INTERRUPT_ACTIVE));
155 while ((hr =
ITHISCALL(dbgCtrl, WaitForEvent, DEBUG_WAIT_DEFAULT,
timeout)) == S_FALSE) {
167 ITHISCALL(dbgCtrl, GetLastEventInformation, &
Type, &ProcessId, &ThreadId,
NULL, 0,
NULL,
NULL, 0,
NULL);
185 case DEBUG_EVENT_BREAKPOINT:
188 case DEBUG_EVENT_EXCEPTION: {
189 EXCEPTION_RECORD64 exr;
190 ITHISCALL(dbgCtrl, GetLastEventInformation, &
Type, &ProcessId, &ThreadId, &exr,
sizeof(exr),
NULL,
NULL, 0,
NULL);
198 case DEBUG_EVENT_EXIT_PROCESS:
201 case DEBUG_EVENT_CREATE_PROCESS:
216 if (SUCCEEDED(
ITHISCALL(dbgCtrl, SetExecutionStatus, DEBUG_STATUS_STEP_OVER))) {
223 static volatile LONG bp_idx = 0;
228 ULONG type =
b->hw ? DEBUG_BREAKPOINT_DATA : DEBUG_BREAKPOINT_CODE;
229 PDEBUG_BREAKPOINT bkpt;
230 if (FAILED(
ITHISCALL(dbgCtrl, GetBreakpointById,
b->internal, &bkpt))) {
235 }
while (hr == E_INVALIDARG);
242 flags = set ?
flags | DEBUG_BREAKPOINT_ENABLED :
flags & ~DEBUG_BREAKPOINT_ENABLED;
244 ULONG access_type = 0;
246 access_type |= DEBUG_BREAK_EXECUTE;
249 access_type |= DEBUG_BREAK_READ;
252 access_type |= DEBUG_BREAK_WRITE;
255 access_type |= DEBUG_BREAK_READ;
256 access_type |= DEBUG_BREAK_WRITE;
258 THISCALL(bkpt, SetDataParameters,
b->size, access_type);
277 if (
type == IMAGE_FILE_MACHINE_IA64 ||
type == IMAGE_FILE_MACHINE_AMD64) {
279 }
else if (
type == IMAGE_FILE_MACHINE_I386) {
281 }
else if (
type == IMAGE_FILE_MACHINE_ARM) {
293 if (!idbg || !idbg->
initialized || FAILED(
ITHISCALL(dbgCtrl, GetActualProcessorType, &ptype))) {
296 if (ptype == IMAGE_FILE_MACHINE_IA64 || ptype == IMAGE_FILE_MACHINE_AMD64) {
299 }
else if (ptype == IMAGE_FILE_MACHINE_I386) {
305 }
else if (ptype == IMAGE_FILE_MACHINE_ARM) {
326 const size_t frame_cnt = 128;
327 PDEBUG_STACK_FRAME dbgframes =
RZ_NEWS(DEBUG_STACK_FRAME, frame_cnt);
332 if (FAILED(
ITHISCALL(dbgCtrl, GetStackTrace, 0, 0, 0, dbgframes, frame_cnt, &frames_filled))) {
338 for (
i = 0;
i < frames_filled;
i++) {
343 f->sp = dbgframes[
i].StackOffset;
344 f->bp = dbgframes[
i].FrameOffset;
345 f->addr = dbgframes[
i].ReturnOffset;
346 f->size =
f->bp -
f->sp;
355 ULONG mod_cnt, mod_un_cnt;
356 if (FAILED(
ITHISCALL(dbgSymbols, GetNumberModules, &mod_cnt, &mod_un_cnt))) {
362 PDEBUG_MODULE_PARAMETERS params =
RZ_NEWS(DEBUG_MODULE_PARAMETERS, mod_cnt);
366 if (FAILED(
ITHISCALL(dbgSymbols, GetModuleParameters, mod_cnt, 0, 0, params))) {
374 for (
i = 0;
i < mod_cnt;
i++) {
375 char *mod_name =
malloc(params[
i].ModuleNameSize);
376 char *image_name =
malloc(params[
i].ImageNameSize);
377 if (!mod_name || !image_name) {
384 DEBUG_ANY_ID, params[
i].Base,
385 image_name, params[
i].ImageNameSize,
NULL,
386 mod_name, params[
i].ModuleNameSize,
NULL,
408 MEMORY_BASIC_INFORMATION64 mbi;
412 PIMAGE_NT_HEADERS64
h =
RZ_NEWS(IMAGE_NT_HEADERS64, mod_cnt);
413 PIMAGE_SECTION_HEADER *
s =
RZ_NEWS0(PIMAGE_SECTION_HEADER, mod_cnt);
417 rz_list_foreach (mod_list, it,
mod) {
418 if (FAILED(
ITHISCALL(dbgData, ReadImageNtHeaders,
mod->addr,
h +
i))) {
419 memset(
h +
i, 0,
sizeof(IMAGE_NT_HEADERS64));
421 IMAGE_DOS_HEADER dos;
423 const size_t header_size =
h[
i].OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR32_MAGIC
424 ?
sizeof(IMAGE_NT_HEADERS32)
425 :
sizeof(IMAGE_NT_HEADERS64);
426 ULONG64
offset =
mod->addr + dos.e_lfanew + header_size;
427 const ULONG size =
sizeof(IMAGE_SECTION_HEADER) *
h[
i].FileHeader.NumberOfSections;
434 ITHISCALL(dbgCtrl, GetPageSize, &page_size);
435 ULONG p_mask = page_size - 1;
436 while (SUCCEEDED(
ITHISCALL(dbgData, QueryVirtual,
to, &mbi))) {
437 to = mbi.BaseAddress + mbi.RegionSize;
439 perm |= mbi.Protect & PAGE_READONLY ?
RZ_PERM_R : 0;
440 perm |= mbi.Protect & PAGE_READWRITE ?
RZ_PERM_RW : 0;
441 perm |= mbi.Protect & PAGE_EXECUTE ?
RZ_PERM_X : 0;
442 perm |= mbi.Protect & PAGE_EXECUTE_READ ?
RZ_PERM_RX : 0;
443 perm |= mbi.Protect & PAGE_EXECUTE_READWRITE ?
RZ_PERM_RWX : 0;
444 perm = mbi.Protect & PAGE_NOACCESS ? 0 : perm;
449 if (mbi.Type == MEM_IMAGE) {
451 rz_list_foreach (mod_list, it,
mod) {
452 if (mbi.BaseAddress >=
mod->addr && mbi.BaseAddress <
mod->addr +
mod->size) {
457 if (
i < mod_cnt &&
mod) {
459 for (j = 0; j <
h[
i].FileHeader.NumberOfSections; j++) {
460 ut64 sect_vaddr =
mod->addr +
s[
i][j].VirtualAddress;
461 ut64 sect_vsize = (((
ut64)
s[
i][j].Misc.VirtualSize) + p_mask) & ~p_mask;
462 if (mbi.BaseAddress >= sect_vaddr && mbi.BaseAddress < sect_vaddr + sect_vsize) {
475 for (
i = 0;
i < mod_cnt;
i++) {
488 if (SUCCEEDED(
ITHISCALL(dbgSysObj, GetCurrentProcessSystemId, &Id))) {
489 if (Id ==
pid && SUCCEEDED(
ITHISCALL(dbgSysObj, GetCurrentThreadSystemId, &Id))) {
493 if (SUCCEEDED(
ITHISCALL(dbgClient, AttachProcess, idbg->
server,
pid, DEBUG_ATTACH_DEFAULT))) {
502 return SUCCEEDED(
ITHISCALL(dbgClient, DetachProcesses));
511 ULONG exit_code,
class, qualifier;
512 if (SUCCEEDED(
ITHISCALL(dbgCtrl, GetDebuggeeType, &
class, &qualifier))) {
513 if (
class == DEBUG_CLASS_UNINITIALIZED) {
520 if (FAILED(
ITHISCALL(dbgClient, GetExitCode, &exit_code))) {
523 return exit_code == STILL_ACTIVE;
525 HRESULT hr =
ITHISCALL(dbgClient, TerminateProcesses);
526 return SUCCEEDED(hr);
532 ULONG thread_cnt = 0;
533 ITHISCALL(dbgSysObj, GetNumberThreads, &thread_cnt);
540 if (!
list || !threads_ids || !threads_sysids) {
543 free(threads_sysids);
546 ITHISCALL(dbgSysObj, GetThreadIdsByIndex, 0, thread_cnt, threads_ids, threads_sysids);
548 for (
i = 0;
i < thread_cnt;
i++) {
550 ITHISCALL(dbgSysObj, SetCurrentThreadId, threads_ids[
i]);
556 free(threads_sysids);
563 char exeinfo[MAX_PATH];
564 char cmdline[MAX_PATH];
565 if (SUCCEEDED(
ITHISCALL(dbgClient, GetRunningProcessDescription, idbg->
server,
dbg->
pid, DEBUG_PROC_DESC_NO_SERVICES | DEBUG_PROC_DESC_NO_MTS_PACKAGES, exeinfo, MAX_PATH,
NULL, cmdline, MAX_PATH,
NULL))) {
592 ITHISCALL(dbgClient, WriteDumpFile,
path, DEBUG_DUMP_DEFAULT);
603 if (SUCCEEDED(
ITHISCALL(dbgClient, GetRunningProcessSystemIds,
604 idbg->
server, ids, _countof(ids), &ids_cnt))) {
606 for (
i = 0;
i < ids_cnt;
i++) {
608 if (SUCCEEDED(
ITHISCALL(dbgClient, GetRunningProcessDescription,
609 idbg->
server, ids[
i], DEBUG_PROC_DESC_DEFAULT,
623 .arch =
"x86,x64,arm,arm64",
648 #ifndef RZ_PLUGIN_INCORE
RzBinInfo * info(RzBinFile *bf)
#define EXCEPTION_SINGLE_STEP
#define EXCEPTION_GUARD_PAGE
#define EXCEPTION_FLT_STACK_CHECK
#define EXCEPTION_INT_DIVIDE_BY_ZERO
#define EXCEPTION_FLT_UNDERFLOW
#define EXCEPTION_FLT_OVERFLOW
#define EXCEPTION_FLT_DENORMAL_OPERAND
#define EXCEPTION_FLT_INEXACT_RESULT
#define EXCEPTION_ILLEGAL_INSTRUCTION
#define EXCEPTION_ACCESS_VIOLATION
#define EXCEPTION_BREAKPOINT
#define EXCEPTION_FLT_INVALID_OPERATION
#define EXCEPTION_FLT_DIVIDE_BY_ZERO
RZ_API void rz_cons_break_pop(void)
RZ_API void rz_cons_break_push(RzConsBreak cb, void *user)
static static fork const void static count static fd const char const char static newpath const char static path const char path
static char * windbg_reg_profile(RzDebug *dbg)
static bool windbg_gcore(RzDebug *dbg, char *p, RzBuffer *dest)
static RzDebugInfo * windbg_info(RzDebug *dbg, const char *arg)
#define DEBUG_DUMP_ACTIVE
static int windbg_attach(RzDebug *dbg, int pid)
RzDebugPlugin rz_debug_plugin_windbg
static void break_debugger(void *user)
static RzList * windbg_map_get(RzDebug *dbg)
#define ITHISCALL(dbginterface, function,...)
static int windbg_detach(RzDebug *dbg, int pid)
static int windbg_breakpoint(RzBreakpoint *bp, RzBreakpointItem *b, bool set)
static bool is_target_kernel(DbgEngContext *idbg)
static RzList * windbg_threads(RzDebug *dbg, int pid)
#define THISCALL(dbginterface, function,...)
RzList * windbg_pids(RzDebug *dbg, int pid)
RZ_API RzLibStruct rizin_plugin
static int windbg_continue(RzDebug *dbg, int pid, int tid, int sig)
static int windbg_reg_write(RzDebug *dbg, int type, const ut8 *buf, int size)
static RzDebugReasonType exception_to_reason(DWORD ExceptionCode)
static RzList * windbg_frames(RzDebug *dbg, ut64 at)
static int windbg_reg_read(RzDebug *dbg, int type, ut8 *buf, int size)
static int windbg_step(RzDebug *dbg)
static bool io_desc_is_windbg(RzIO *io)
static int windbg_wait(RzDebug *dbg, int pid)
#define IMAGE_FILE_MACHINE_ARM64
static int windbg_select(RzDebug *dbg, int pid, int tid)
static int windbg_step_over(RzDebug *dbg)
static int windbg_stop(RzDebug *dbg)
static bool windbg_init(RzDebug *dbg, void **user)
static bool windbg_kill(RzDebug *dbg, int pid, int tid, int sig)
static RzList * windbg_modules_get(RzDebug *dbg)
RZ_API void rz_debug_map_free(RzDebugMap *map)
RZ_API RzDebugMap * rz_debug_map_new(char *name, ut64 addr, ut64 addr_end, int perm, int user)
size_t map(int syms, int left, int len)
RZ_API char * sdb_fmt(const char *fmt,...)
RZ_API void Ht_() free(HtName_(Ht) *ht)
return memset(p, 0, total)
static void list(RzEgg *egg)
RZ_API RZ_OWN RzList * rz_list_newf(RzListFree f)
Returns a new initialized RzList pointer and sets the free method.
RZ_API ut32 rz_list_length(RZ_NONNULL const RzList *list)
Returns the length of the list.
RZ_API RZ_BORROW RzListIter * rz_list_append(RZ_NONNULL RzList *list, void *data)
Appends at the end of the list a new element.
RZ_API void rz_list_free(RZ_NONNULL RzList *list)
Empties the list and frees the list pointer.
void * malloc(size_t size)
static static fork const void static count static fd const char const char static newpath char char char static envp time_t static t const char static mode static whence const char static dir time_t static t unsigned static seconds const char struct utimbuf static buf static inc pid
return strdup("=SP r13\n" "=LR r14\n" "=PC r15\n" "=A0 r0\n" "=A1 r1\n" "=A2 r2\n" "=A3 r3\n" "=ZF zf\n" "=SF nf\n" "=OF vf\n" "=CF cf\n" "=SN or0\n" "gpr lr .32 56 0\n" "gpr pc .32 60 0\n" "gpr cpsr .32 64 0 ____tfiae_________________qvczn\n" "gpr or0 .32 68 0\n" "gpr tf .1 64.5 0 thumb\n" "gpr ef .1 64.9 0 endian\n" "gpr jf .1 64.24 0 java\n" "gpr qf .1 64.27 0 sticky_overflow\n" "gpr vf .1 64.28 0 overflow\n" "gpr cf .1 64.29 0 carry\n" "gpr zf .1 64.30 0 zero\n" "gpr nf .1 64.31 0 negative\n" "gpr itc .4 64.10 0 if_then_count\n" "gpr gef .4 64.16 0 great_or_equal\n" "gpr r0 .32 0 0\n" "gpr r1 .32 4 0\n" "gpr r2 .32 8 0\n" "gpr r3 .32 12 0\n" "gpr r4 .32 16 0\n" "gpr r5 .32 20 0\n" "gpr r6 .32 24 0\n" "gpr r7 .32 28 0\n" "gpr r8 .32 32 0\n" "gpr r9 .32 36 0\n" "gpr r10 .32 40 0\n" "gpr r11 .32 44 0\n" "gpr r12 .32 48 0\n" "gpr r13 .32 52 0\n" "gpr r14 .32 56 0\n" "gpr r15 .32 60 0\n" "gpr r16 .32 64 0\n" "gpr r17 .32 68 0\n")
RZ_API RzDebugPid * rz_debug_pid_free(RzDebugPid *pid)
RZ_API RzDebugPid * rz_debug_pid_new(const char *path, int pid, int uid, char status, ut64 pc)
#define rz_return_val_if_fail(expr, val)
@ RZ_DEBUG_REASON_ILLEGAL
@ RZ_DEBUG_REASON_BREAKPOINT
@ RZ_DEBUG_REASON_USERSUSP
@ RZ_DEBUG_REASON_SEGFAULT
@ RZ_DEBUG_REASON_NEW_PID
@ RZ_DEBUG_REASON_EXIT_PID
@ RZ_DEBUG_REASON_DIVBYZERO
void(* RzListFree)(void *ptr)
RZ_API char * rz_str_appendf(char *ptr, const char *fmt,...) RZ_PRINTF_CHECK(2
#define RZ_STR_ISEMPTY(x)
RZ_API char * rz_sys_getenv(const char *key)
Get the value of an environment variable named key or NULL if none exists.
RZ_API char * rz_sys_getdir(void)
Get current working directory.
RZ_API ut64 rz_time_now(void)
Returns the current time in microseconds.
static struct sockaddr static addrlen static backlog const void static flags void struct sockaddr socklen_t static fromlen const void const struct sockaddr to
static struct sockaddr static addrlen static backlog const void static flags void flags
DWORD lastExecutionStatus
PDEBUG_SYSTEM_OBJECTS4 dbgSysObj
PDEBUG_SYMBOLS3 dbgSymbols
PDEBUG_DATA_SPACES4 dbgData
PDEBUG_ADVANCED3 dbgAdvanced
struct rz_io_plugin_t * plugin
struct rz_io_desc_t * desc
ut64(WINAPI *w32_GetEnabledXStateFeatures)()