mirror of
https://github.com/Ed94/raddebugger.git
synced 2026-07-26 09:23:44 +00:00
fill out first pass implementations of raddbg_markup features; thread names, thread colors, format-string output-debug-string helper, attachment-checking
This commit is contained in:
+34
-5
@@ -606,8 +606,8 @@ ctrl_event_from_serialized_string(Arena *arena, String8 string)
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.stack_base);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.tls_root);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.timestamp);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.exception_code);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.rgba);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.exception_code);
|
||||
read_off += str8_deserial_read_struct(string, read_off, &event.string.size);
|
||||
event.string.str = push_array_no_zero(arena, U8, event.string.size);
|
||||
read_off += str8_deserial_read(string, read_off, event.string.str, event.string.size, 1);
|
||||
@@ -3603,6 +3603,7 @@ ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_
|
||||
Guid rdi_dbg_guid = {0};
|
||||
String8 rdi_dbg_path = str8_zero();
|
||||
String8 raddbg_data = str8_zero();
|
||||
Rng1U64 raddbg_section_voff_range = r1u64(0, 0);
|
||||
ProfScope("unpack relevant PE info")
|
||||
{
|
||||
B32 is_valid = 1;
|
||||
@@ -3804,7 +3805,6 @@ ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_
|
||||
U64 sec_count = file_header.section_count;
|
||||
COFF_SectionHeader *sec = push_array(scratch.arena, COFF_SectionHeader, sec_count);
|
||||
dmn_process_read(process.dmn_handle, r1u64(vaddr_range.min + sec_array_off, vaddr_range.min + sec_array_off + sec_count*sizeof(COFF_SectionHeader)), sec);
|
||||
Rng1U64 raddbg_section_voff_range = r1u64(0, 0);
|
||||
for EachIndex(idx, sec_count)
|
||||
{
|
||||
String8 section_name = str8_cstring(sec[idx].name);
|
||||
@@ -3820,6 +3820,13 @@ ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_
|
||||
vaddr_range.min + raddbg_section_voff_range.max), raddbg_data.str);
|
||||
scratch_end(scratch);
|
||||
}
|
||||
|
||||
// rjf: if we have a raddbg section, mark the first byte as 1, to signify attachment
|
||||
if(raddbg_section_voff_range.max != raddbg_section_voff_range.min)
|
||||
{
|
||||
U8 new_value = 1;
|
||||
dmn_process_write_struct(process.dmn_handle, vaddr_range.min + raddbg_section_voff_range.min, &new_value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3898,6 +3905,7 @@ ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_
|
||||
node->pdatas_count = pdatas_count;
|
||||
node->entry_point_voff = entry_point_voff;
|
||||
node->initial_debug_info_path = initial_debug_info_path;
|
||||
node->raddbg_section_voff_range = raddbg_section_voff_range;
|
||||
node->raddbg_data = raddbg_data;
|
||||
}
|
||||
}
|
||||
@@ -3905,11 +3913,12 @@ ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_
|
||||
}
|
||||
|
||||
internal void
|
||||
ctrl_thread__module_close(CTRL_Handle module)
|
||||
ctrl_thread__module_close(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_range)
|
||||
{
|
||||
//////////////////////////////
|
||||
//- rjf: evict module image info from cache
|
||||
//
|
||||
Rng1U64 raddbg_section_voff_range = {0};
|
||||
{
|
||||
U64 hash = ctrl_hash_from_handle(module);
|
||||
U64 slot_idx = hash%ctrl_state->module_image_info_cache.slots_count;
|
||||
@@ -3929,11 +3938,21 @@ ctrl_thread__module_close(CTRL_Handle module)
|
||||
}
|
||||
if(node)
|
||||
{
|
||||
raddbg_section_voff_range = node->raddbg_section_voff_range;
|
||||
DLLRemove(slot->first, slot->last, node);
|
||||
arena_release(node->arena);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//////////////////////////////
|
||||
//- rjf: write 0 into first byte of raddbg data section, to signify detachment
|
||||
//
|
||||
if(raddbg_section_voff_range.max != raddbg_section_voff_range.min)
|
||||
{
|
||||
U8 new_value = 0;
|
||||
dmn_process_write_struct(process.dmn_handle, vaddr_range.min + raddbg_section_voff_range.min, &new_value);
|
||||
}
|
||||
}
|
||||
|
||||
//- rjf: attached process running/event gathering
|
||||
@@ -4265,13 +4284,14 @@ ctrl_thread__next_dmn_event(Arena *arena, DMN_CtrlCtx *ctrl_ctx, CTRL_Msg *msg,
|
||||
{
|
||||
CTRL_Event *out_evt = ctrl_event_list_push(scratch.arena, &evts);
|
||||
CTRL_Handle module_handle = ctrl_handle_make(CTRL_MachineID_Local, event->module);
|
||||
CTRL_Entity *module_ent = ctrl_entity_from_handle(ctrl_state->ctrl_thread_entity_store, module_handle);
|
||||
CTRL_Entity *process_ent = ctrl_process_from_entity(module_ent);
|
||||
String8 module_path = event->string;
|
||||
ctrl_thread__module_close(module_handle);
|
||||
ctrl_thread__module_close(process_ent->handle, module_handle, module_ent->vaddr_range);
|
||||
out_evt->kind = CTRL_EventKind_EndModule;
|
||||
out_evt->msg_id = msg->msg_id;
|
||||
out_evt->entity = module_handle;
|
||||
out_evt->string = module_path;
|
||||
CTRL_Entity *module_ent = ctrl_entity_from_handle(ctrl_state->ctrl_thread_entity_store, module_handle);
|
||||
CTRL_Entity *debug_info_path_ent = ctrl_entity_child_from_kind(module_ent, CTRL_EntityKind_DebugInfoPath);
|
||||
if(debug_info_path_ent != &ctrl_entity_nil)
|
||||
{
|
||||
@@ -4302,6 +4322,15 @@ ctrl_thread__next_dmn_event(Arena *arena, DMN_CtrlCtx *ctrl_ctx, CTRL_Msg *msg,
|
||||
out_evt->string = event->string;
|
||||
out_evt->entity_id = event->code;
|
||||
}break;
|
||||
case DMN_EventKind_SetThreadColor:
|
||||
{
|
||||
CTRL_Event *out_evt = ctrl_event_list_push(scratch.arena, &evts);
|
||||
out_evt->kind = CTRL_EventKind_ThreadColor;
|
||||
out_evt->msg_id = msg->msg_id;
|
||||
out_evt->entity = ctrl_handle_make(CTRL_MachineID_Local, event->thread);
|
||||
out_evt->parent = ctrl_handle_make(CTRL_MachineID_Local, event->process);
|
||||
out_evt->rgba = event->code;
|
||||
}break;
|
||||
}
|
||||
ctrl_c2u_push_events(&evts);
|
||||
|
||||
|
||||
@@ -593,6 +593,7 @@ struct CTRL_ModuleImageInfoCacheNode
|
||||
U64 entry_point_voff;
|
||||
Rng1U64 tls_vaddr_range;
|
||||
String8 initial_debug_info_path;
|
||||
Rng1U64 raddbg_section_voff_range;
|
||||
String8 raddbg_data;
|
||||
};
|
||||
|
||||
@@ -953,7 +954,7 @@ internal void ctrl_thread__append_resolved_process_user_bp_traps(Arena *arena, C
|
||||
|
||||
//- rjf: module lifetime open/close work
|
||||
internal void ctrl_thread__module_open(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_range, String8 path);
|
||||
internal void ctrl_thread__module_close(CTRL_Handle module);
|
||||
internal void ctrl_thread__module_close(CTRL_Handle process, CTRL_Handle module, Rng1U64 vaddr_range);
|
||||
|
||||
//- rjf: attached process running/event gathering
|
||||
internal DMN_Event *ctrl_thread__next_dmn_event(Arena *arena, DMN_CtrlCtx *ctrl_ctx, CTRL_Msg *msg, DMN_RunCtrls *run_ctrls, CTRL_Spoof *spoof);
|
||||
|
||||
@@ -21,6 +21,7 @@ DMN_EventKindTable:
|
||||
{Memory}
|
||||
{DebugString}
|
||||
{SetThreadName}
|
||||
{SetThreadColor}
|
||||
}
|
||||
|
||||
@table(name)
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
//- GENERATED CODE
|
||||
|
||||
C_LINKAGE_BEGIN
|
||||
String8 dmn_event_kind_string_table[17] =
|
||||
String8 dmn_event_kind_string_table[18] =
|
||||
{
|
||||
str8_lit_comp("Null"),
|
||||
str8_lit_comp("Error"),
|
||||
@@ -23,6 +23,7 @@ str8_lit_comp("Halt"),
|
||||
str8_lit_comp("Memory"),
|
||||
str8_lit_comp("DebugString"),
|
||||
str8_lit_comp("SetThreadName"),
|
||||
str8_lit_comp("SetThreadColor"),
|
||||
};
|
||||
|
||||
String8 dmn_exception_kind_string_table[5] =
|
||||
|
||||
@@ -25,6 +25,7 @@ DMN_EventKind_Halt,
|
||||
DMN_EventKind_Memory,
|
||||
DMN_EventKind_DebugString,
|
||||
DMN_EventKind_SetThreadName,
|
||||
DMN_EventKind_SetThreadColor,
|
||||
DMN_EventKind_COUNT,
|
||||
} DMN_EventKind;
|
||||
|
||||
@@ -58,7 +59,7 @@ DMN_ExceptionKind_COUNT,
|
||||
} DMN_ExceptionKind;
|
||||
|
||||
C_LINKAGE_BEGIN
|
||||
extern String8 dmn_event_kind_string_table[17];
|
||||
extern String8 dmn_event_kind_string_table[18];
|
||||
extern String8 dmn_exception_kind_string_table[5];
|
||||
|
||||
C_LINKAGE_END
|
||||
|
||||
@@ -2378,6 +2378,13 @@ dmn_ctrl_run(Arena *arena, DMN_CtrlCtx *ctx, DMN_RunCtrls *ctrls)
|
||||
}
|
||||
}break;
|
||||
|
||||
//- rjf: fill set-thread-color info
|
||||
case DMN_W32_EXCEPTION_RADDBG_SET_THREAD_COLOR:
|
||||
{
|
||||
e->kind = DMN_EventKind_SetThreadColor;
|
||||
e->code = exception->ExceptionInformation[1];
|
||||
}break;
|
||||
|
||||
//- rjf: unhandled exception case
|
||||
default:
|
||||
{
|
||||
|
||||
@@ -56,6 +56,7 @@
|
||||
#define DMN_W32_EXCEPTION_SET_THREAD_NAME 0x406d1388u
|
||||
#define DMN_w32_EXCEPTION_CLRDBG_NOTIFICATION 0x04242420u
|
||||
#define DMN_w32_EXCEPTION_CLR 0xE0434352u
|
||||
#define DMN_W32_EXCEPTION_RADDBG_SET_THREAD_COLOR 0x00524144u
|
||||
|
||||
////////////////////////////////
|
||||
//~ rjf: Win32 Register Codes
|
||||
|
||||
@@ -7,23 +7,37 @@
|
||||
////////////////////////////////
|
||||
//~ Implementation Overrides
|
||||
|
||||
#if !defined(raddbg_markup_vsnprintf)
|
||||
# define raddbg_markup_vsnprintf vsnprintf
|
||||
#if !defined(RADDBG_MARKUP_VSNPRINTF)
|
||||
# define RADDBG_MARKUP_DEFAULT_VSNPRINTF 1
|
||||
# define RADDBG_MARKUP_VSNPRINTF vsnprintf
|
||||
#endif
|
||||
|
||||
////////////////////////////////
|
||||
//~ Usage Macros
|
||||
|
||||
#define raddbg_is_attached(...) raddbg_is_attached__impl()
|
||||
#define raddbg_thread_name(fmt, ...) raddbg_thread_name__impl((fmt), __VA_ARGS__)
|
||||
#define raddbg_thread_color_hex(hexcode) raddbg_thread_color__impl((hexcode))
|
||||
#define raddbg_thread_color_rgba(r, g, b, a) raddbg_thread_color__impl((unsigned int)(((r)*255) << 24) | (unsigned int)(((g)*255) << 16) | (unsigned int)(((b)*255) << 8) | (unsigned int)((a)*255))
|
||||
#define raddbg_break(...) raddbg_break__impl()
|
||||
#define raddbg_break_if(expr, ...) ((expr) ? raddbg_break__impl() : (void)0)
|
||||
#define raddbg_watch(fmt, ...) raddbg_watch__impl((fmt), __VA_ARGS__)
|
||||
#define raddbg_pin(expr, ...) /* NOTE(rjf): inspected by debugger ui - does not change program execution */
|
||||
#define raddbg_log(fmt, ...) raddbg_log__impl((fmt), __VA_ARGS__)
|
||||
#define raddbg_auto_view_rule(type, ...) raddbg_exe_data static char raddbg_glue(raddbg_auto_view_rule_data__, __COUNTER__)[] = ("auto_view_rule: {type: \"" #type "\", view_rule: \"" #__VA_ARGS__ "\"}")
|
||||
#if defined(RADDBG_MARKUP_STUBS)
|
||||
# define raddbg_is_attached(...) (0)
|
||||
# define raddbg_thread_name(fmt, ...) ((void)0)
|
||||
# define raddbg_thread_color_hex(hexcode) ((void)0)
|
||||
# define raddbg_thread_color_rgba(r, g, b, a) ((void)0)
|
||||
# define raddbg_break(...) ((void)0)
|
||||
# define raddbg_break_if(expr, ...) ((void)0)
|
||||
# define raddbg_watch(fmt, ...) ((void)0)
|
||||
# define raddbg_pin(expr, ...)
|
||||
# define raddbg_log(fmt, ...) ((void)0)
|
||||
# define raddbg_auto_view_rule(type, ...) struct raddbg_glue(raddbg_auto_view_rule_stub__, __COUNTER__){int __unused__}
|
||||
#else
|
||||
# define raddbg_is_attached(...) raddbg_is_attached__impl()
|
||||
# define raddbg_thread_name(fmt, ...) raddbg_thread_name__impl((fmt), __VA_ARGS__)
|
||||
# define raddbg_thread_color_hex(hexcode) raddbg_thread_color__impl((hexcode))
|
||||
# define raddbg_thread_color_rgba(r, g, b, a) raddbg_thread_color__impl((unsigned int)(((r)*255) << 24) | (unsigned int)(((g)*255) << 16) | (unsigned int)(((b)*255) << 8) | (unsigned int)((a)*255))
|
||||
# define raddbg_break(...) raddbg_break__impl()
|
||||
# define raddbg_break_if(expr, ...) ((expr) ? raddbg_break__impl() : (void)0)
|
||||
# define raddbg_watch(fmt, ...) raddbg_watch__impl((fmt), __VA_ARGS__)
|
||||
# define raddbg_pin(expr, ...) /* NOTE(rjf): inspected by debugger ui - does not change program execution */
|
||||
# define raddbg_log(fmt, ...) raddbg_log__impl((fmt), __VA_ARGS__)
|
||||
# define raddbg_auto_view_rule(type, ...) raddbg_exe_data static char raddbg_glue(raddbg_auto_view_rule_data__, __COUNTER__)[] = ("auto_view_rule: {type: \"" #type "\", view_rule: \"" #__VA_ARGS__ "\"}")
|
||||
#endif
|
||||
|
||||
////////////////////////////////
|
||||
//~ Helpers
|
||||
@@ -34,13 +48,21 @@
|
||||
////////////////////////////////
|
||||
//~ Win32 Implementations
|
||||
|
||||
#if defined(RADDBG_MARKUP_IMPLEMENTATION)
|
||||
#if defined(RADDBG_MARKUP_IMPLEMENTATION) && !defined(RADDBG_MARKUP_STUBS)
|
||||
#if defined(_WIN32)
|
||||
|
||||
//- default includes
|
||||
#if RADDBG_MARKUP_DEFAULT_VSNPRINTF
|
||||
#include <stdio.h>
|
||||
#endif
|
||||
|
||||
//- section allocating
|
||||
#pragma section(".raddbg", read)
|
||||
#pragma section(".raddbg", read, write)
|
||||
#define raddbg_exe_data __declspec(allocate(".raddbg"))
|
||||
|
||||
//- first byte of exe data section -> is attached
|
||||
raddbg_exe_data unsigned char raddbg_is_attached_byte_marker = 0;
|
||||
|
||||
//- types
|
||||
|
||||
typedef int BOOL;
|
||||
@@ -72,11 +94,12 @@ extern "C"
|
||||
__declspec(dllimport) HANDLE GetCurrentThread(void);
|
||||
__declspec(dllimport) DWORD GetCurrentThreadId(void);
|
||||
__declspec(dllimport) void RaiseException(DWORD dwExceptionCode, DWORD dwExceptionFlags, DWORD nNumberOfArguments, const ULONG_PTR *lpArguments);
|
||||
__declspec(dllimport) void OutputDebugStringA(LPCSTR buffer);
|
||||
long long _InterlockedCompareExchange64(long long volatile*, long long, long long);
|
||||
long long _InterlockedExchangeAdd64(long long volatile*, long long);
|
||||
#pragma intrinsic(_InterlockedCompareExchange64)
|
||||
#pragma intrinsic(_InterlockedExchangeAdd64)
|
||||
int raddbg_markup_vsnprintf(char * const, unsigned long long const, const char * const, va_list);
|
||||
int RADDBG_MARKUP_VSNPRINTF(char * const, unsigned long long const, const char * const, va_list);
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
#endif
|
||||
@@ -173,8 +196,7 @@ raddbg_encode_utf16(wchar_t *str, unsigned __int32 codepoint)
|
||||
static inline int
|
||||
raddbg_is_attached__impl(void)
|
||||
{
|
||||
// TODO(rjf)
|
||||
return 0;
|
||||
return !!raddbg_is_attached_byte_marker;
|
||||
}
|
||||
|
||||
static inline void
|
||||
@@ -186,7 +208,7 @@ raddbg_thread_name__impl(char *fmt, ...)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
raddbg_markup_vsnprintf(buffer, sizeof(buffer), fmt, args);
|
||||
RADDBG_MARKUP_VSNPRINTF(buffer, sizeof(buffer), fmt, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
@@ -260,7 +282,32 @@ raddbg_thread_name__impl(char *fmt, ...)
|
||||
static inline void
|
||||
raddbg_thread_color__impl(unsigned int hexcode)
|
||||
{
|
||||
// TODO(rjf)
|
||||
if(raddbg_is_attached())
|
||||
{
|
||||
#pragma pack(push, 8)
|
||||
typedef struct RADDBG_ThreadColorInfo RADDBG_ThreadColorInfo;
|
||||
struct RADDBG_ThreadColorInfo
|
||||
{
|
||||
DWORD dwThreadID;
|
||||
DWORD _pad0_;
|
||||
DWORD rgba;
|
||||
DWORD _pad1_;
|
||||
};
|
||||
#pragma pack(pop)
|
||||
RADDBG_ThreadColorInfo info;
|
||||
info.dwThreadID = GetCurrentThreadId();
|
||||
info.rgba = hexcode;
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable: 6320 6322)
|
||||
__try
|
||||
{
|
||||
RaiseException(0x00524144u, 0, sizeof(info) / sizeof(void *), (const ULONG_PTR *)&info);
|
||||
}
|
||||
__except(1)
|
||||
{
|
||||
}
|
||||
#pragma warning(pop)
|
||||
}
|
||||
}
|
||||
|
||||
#define raddbg_break__impl() (__debugbreak())
|
||||
@@ -274,7 +321,17 @@ raddbg_watch__impl(char *fmt, ...)
|
||||
static inline void
|
||||
raddbg_log__impl(char *fmt, ...)
|
||||
{
|
||||
// TODO(rjf)
|
||||
// rjf: resolve variadic arguments
|
||||
char buffer[4096];
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, fmt);
|
||||
RADDBG_MARKUP_VSNPRINTF(buffer, sizeof(buffer), fmt, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
// rjf: output debug string
|
||||
OutputDebugStringA(buffer);
|
||||
}
|
||||
|
||||
#endif // defined(_WIN32)
|
||||
|
||||
@@ -2670,7 +2670,15 @@ dynamic_step_test(void){
|
||||
////////////////////////////////
|
||||
|
||||
int
|
||||
mule_main(int argc, char** argv){
|
||||
mule_main(int argc, char** argv)
|
||||
{
|
||||
raddbg_thread_name("mule_main_thread");
|
||||
raddbg_thread_color_rgba(1, 0, 0, 1);
|
||||
if(raddbg_is_attached())
|
||||
{
|
||||
raddbg_log("raddbg is attached!\n");
|
||||
}
|
||||
|
||||
mule_init();
|
||||
|
||||
// NOTE(allen): Eval Tests
|
||||
@@ -2735,5 +2743,3 @@ mule_main(int argc, char** argv){
|
||||
|
||||
return(0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -3114,6 +3114,8 @@ rd_eval_space_write(void *u, E_Space space, void *in, Rng1U64 range)
|
||||
MD_Node *child_schema = md_child_from_string(root_schema, child_key, 0);
|
||||
if(str8_match(child_schema->string, str8_lit("label"), 0))
|
||||
{
|
||||
result = 1;
|
||||
ctrl_entity_equip_string(d_state->ctrl_entity_store, entity, write_string);
|
||||
rd_cmd(D_CmdKind_SetEntityName, .ctrl_entity = entity->handle, .string = write_string);
|
||||
}
|
||||
else if(str8_match(child_schema->string, str8_lit("dbg"), 0))
|
||||
|
||||
Reference in New Issue
Block a user