Skip to content
Draft
1 change: 1 addition & 0 deletions src/libdrakvuf/libdrakvuf.h
Original file line number Diff line number Diff line change
Expand Up @@ -786,6 +786,7 @@ addr_t drakvuf_get_function_return_address(drakvuf_t drakvuf, drakvuf_trap_info_

bool drakvuf_get_pid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid) NOEXCEPT;
bool drakvuf_get_tid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, uint32_t* tid) NOEXCEPT;
bool drakvuf_get_pid_from_thread_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid) NOEXCEPT;

bool drakvuf_set_vcpu_gprs(drakvuf_t drakvuf, unsigned int vcpu, registers_t* regs) NOEXCEPT;
void drakvuf_copy_gpr_registers(x86_registers_t* dst, x86_registers_t* src);
Expand Down
14 changes: 14 additions & 0 deletions src/libdrakvuf/os.c
Original file line number Diff line number Diff line change
Expand Up @@ -1070,6 +1070,20 @@ bool drakvuf_get_tid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, a
return ret;
}

bool drakvuf_get_pid_from_thread_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid)
{
bool ret = false;

if ( drakvuf->osi.get_pid_from_thread_handle )
{
drakvuf_lock_and_get_vmi(drakvuf);
ret = drakvuf->osi.get_pid_from_thread_handle(drakvuf, info, handle, pid);
drakvuf_release_vmi(drakvuf);
}

return ret;
}

bool drakvuf_get_wow_context(drakvuf_t drakvuf, addr_t ethread, addr_t* wow_ctx)
{
bool ret = false;
Expand Down
3 changes: 3 additions & 0 deletions src/libdrakvuf/os.h
Original file line number Diff line number Diff line change
Expand Up @@ -279,6 +279,9 @@ typedef struct os_interface
bool (*get_tid_from_handle)
(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, uint32_t* tid);

bool (*get_pid_from_thread_handle)
(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid);

bool (*is_process_suspended)
(drakvuf_t drakvuf, addr_t process, bool* status);

Expand Down
45 changes: 43 additions & 2 deletions src/libdrakvuf/win-processes.c
Original file line number Diff line number Diff line change
Expand Up @@ -703,7 +703,6 @@ bool win_get_current_thread_previous_mode(drakvuf_t drakvuf,
privilege_mode_t* previous_mode )
{
addr_t kthread = win_get_current_thread(drakvuf, info);
PRINT_DEBUG("kthread: %lx\n", kthread);
return win_get_thread_previous_mode(drakvuf, kthread, previous_mode);
}

Expand Down Expand Up @@ -1983,7 +1982,7 @@ bool win_get_pid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_

bool win_get_tid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, uint32_t* tid)
{
if (handle == 0 || handle == UINT64_MAX)
if (handle == 0 || handle == UINT64_MAX - 1)
{
*tid = info->proc_data.tid;
return false;
Expand All @@ -2003,3 +2002,45 @@ bool win_get_tid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_
addr_t ethread = obj + drakvuf->offsets[OBJECT_HEADER_BODY];
return win_get_thread_id(drakvuf, ethread, tid);
}


bool win_get_pid_from_thread_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid)
{
if (handle == 0 || handle == UINT64_MAX - 1)
{
*pid = info->proc_data.pid;
return false;
}

if (!info->proc_data.base_addr || !pid)
return false;

addr_t obj = drakvuf_get_obj_by_handle(drakvuf, info->proc_data.base_addr, handle);
if (!obj)
return false;

addr_t ethread = obj + drakvuf->offsets[OBJECT_HEADER_BODY];

addr_t kthread = ethread + drakvuf->offsets[ETHREAD_TCB];

addr_t eprocess = 0;
addr_t eprocess_ptr_addr = kthread + drakvuf->offsets[KTHREAD_PROCESS];

ACCESS_CONTEXT(ctx,
.translate_mechanism = VMI_TM_PROCESS_PID,
.pid = 0,
.addr = eprocess_ptr_addr,
);

if (VMI_SUCCESS != vmi_read_addr(drakvuf->vmi, &ctx, &eprocess))
{
return false;
}

if (!eprocess)
{
return false;
}

return win_get_process_pid(drakvuf, eprocess, pid);
}
1 change: 1 addition & 0 deletions src/libdrakvuf/win.c
Original file line number Diff line number Diff line change
Expand Up @@ -780,6 +780,7 @@ bool set_os_windows(drakvuf_t drakvuf)
drakvuf->osi.mmvad_protection = win_mmvad_protection;
drakvuf->osi.get_pid_from_handle = win_get_pid_from_handle;
drakvuf->osi.get_tid_from_handle = win_get_tid_from_handle;
drakvuf->osi.get_pid_from_thread_handle = win_get_pid_from_thread_handle;
drakvuf->osi.get_wow_context = win_get_wow_context;
drakvuf->osi.get_user_stack32 = win_get_user_stack32;
drakvuf->osi.get_user_stack64 = win_get_user_stack64;
Expand Down
1 change: 1 addition & 0 deletions src/libdrakvuf/win.h
Original file line number Diff line number Diff line change
Expand Up @@ -207,6 +207,7 @@ uint64_t win_mmvad_protection(drakvuf_t drakvuf, mmvad_info_t* mmvad);

bool win_get_pid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid);
bool win_get_tid_from_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, uint32_t* tid);
bool win_get_pid_from_thread_handle(drakvuf_t drakvuf, drakvuf_trap_info_t* info, addr_t handle, vmi_pid_t* pid);

addr_t win_get_wow_peb(drakvuf_t drakvuf, access_context_t* ctx, addr_t eprocess);
bool win_get_wow_context(drakvuf_t drakvuf, addr_t ethread, addr_t* wow_ctx);
Expand Down
15 changes: 14 additions & 1 deletion src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -250,6 +250,9 @@ static void print_usage()
"\t -S, --syscall-hooks-list <syscalls filter>\n"
"\t File with list of syscalls for trap in syscalls plugin (trap all if parameter is absent)\n"
"\t --disable-sysret Do not monitor syscall results\n"
"\t --syscall-nested-args Nested Arguments field in output\n"
"\t --syscall-dereference-args\n"
"\t Dereference syscall argument values\n"
#endif
#ifdef ENABLE_PLUGIN_PROCMON
"\t -q, --procmon-envs-list <procmon filter>\n"
Expand Down Expand Up @@ -504,6 +507,8 @@ int main(int argc, char** argv)
opt_procdump_disable_kideliverapc_hook,
opt_procdump_disable_kedelayexecutionthread_hook,
opt_procdump_exclude_list,
opt_syscall_dereference_args,
opt_syscall_nested_args,
opt_json_clr,
opt_json_mscorwks,
opt_disable_sysret,
Expand Down Expand Up @@ -593,6 +598,8 @@ int main(int argc, char** argv)
{"procdump-exclude-list", required_argument, NULL, opt_procdump_exclude_list},
{"json-clr", required_argument, NULL, opt_json_clr},
{"json-mscorwks", required_argument, NULL, opt_json_mscorwks},
{"syscall-dereference-args", no_argument, NULL, opt_syscall_dereference_args},
{"syscall-nested-args", no_argument, NULL, opt_syscall_nested_args},
{"syscall-hooks-list", required_argument, NULL, 'S'},
{"procmon-envs-list", required_argument, NULL, 'q'},
{"disable-sysret", no_argument, NULL, opt_disable_sysret},
Expand Down Expand Up @@ -764,11 +771,17 @@ int main(int argc, char** argv)
#endif
#ifdef ENABLE_PLUGIN_SYSCALLS
case 'S':
options.syscalls_filter_file = optarg;
options.syscalls_list_file = optarg;
break;
case opt_disable_sysret:
options.disable_sysret = true;
break;
case opt_syscall_dereference_args:
options.syscalls_dereference_args = true;
break;
case opt_syscall_nested_args:
options.syscalls_nested_args = true;
break;
#endif
#ifdef ENABLE_PLUGIN_PROCMON
case 'q':
Expand Down
2 changes: 2 additions & 0 deletions src/plugins/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,8 @@ sources += syscalls/win.cpp
sources += syscalls/win.h
sources += syscalls/private.h
sources += syscalls/private_2.h
sources += syscalls/parsers_win.cpp
sources += syscalls/parsers_linux.cpp
endif

if PLUGIN_POOLMON
Expand Down
2 changes: 2 additions & 0 deletions src/plugins/meson.build
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@ if get_option('plugin-syscalls')
plugin_sources += 'syscalls/syscalls.cpp'
plugin_sources += 'syscalls/win.cpp'
plugin_sources += 'syscalls/linux.cpp'
plugin_sources += 'syscalls/parsers_win.cpp'
plugin_sources += 'syscalls/parsers_linux.cpp'

config_h.set('ENABLE_PLUGIN_SYSCALLS', 1)

Expand Down
6 changes: 6 additions & 0 deletions src/plugins/output_format/common.h
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,12 @@ struct flagsval

template<class Value>
auto keyval(const char* key, Value&& value)
{
return std::make_pair(std::string(key), std::forward<Value>(value));
}

template<class Value>
auto keyval(std::string key, Value&& value)
{
return std::make_pair(key, std::forward<Value>(value));
}
Expand Down
3 changes: 1 addition & 2 deletions src/plugins/output_format/deffmt.h
Original file line number Diff line number Diff line change
Expand Up @@ -285,12 +285,11 @@ struct DataPrinter
template <class Tk>
static bool print(std::ostream& os, const std::pair<Tk, fmt::Subkey>& data, char sep)
{
const char* parent_key = data.first;
const auto& sub_data = data.second.sub_data;
if (sub_data.empty()) return false;

bool printed = false;
os << parent_key << ":[";
os << std::string(data.first) << ":[";

for (const auto& [sub_key, sub_val] : sub_data)
{
Expand Down
3 changes: 1 addition & 2 deletions src/plugins/output_format/kvfmt.h
Original file line number Diff line number Diff line change
Expand Up @@ -320,7 +320,6 @@ struct DataPrinter
template <class Tk>
static bool print(std::ostream& os, const std::pair<Tk, fmt::Subkey>& data, char sep)
{
const char* parent_key = data.first;
const auto& sub_data = data.second.sub_data;
if (sub_data.empty()) return false;

Expand All @@ -330,7 +329,7 @@ struct DataPrinter
bool printed_prev = printed;
if (printed) os << sep;

std::string flat_key = std::string(parent_key) + "." + sub_key;
std::string flat_key = std::string(data.first) + "." + sub_key;
printed = print_data(os, keyval(flat_key.c_str(), sub_val), sep);

if (!printed && printed_prev) fmt::unputc(os);
Expand Down
4 changes: 3 additions & 1 deletion src/plugins/plugins.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -178,9 +178,11 @@ int drakvuf_plugins::start(const drakvuf_plugin_t plugin_id,
{
syscalls_config config =
{
.syscalls_filter_file = options->syscalls_filter_file,
.syscalls_list_file = options->syscalls_list_file,
.win32k_profile = options->win32k_profile,
.disable_sysret = options->disable_sysret,
.syscalls_dereference_args = options->syscalls_dereference_args,
.syscalls_nested_args = options->syscalls_nested_args,
};
this->plugins[plugin_id] = std::make_unique<syscalls>(this->drakvuf, &config, this->output);
break;
Expand Down
5 changes: 4 additions & 1 deletion src/plugins/plugins.h
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,7 @@ enum dump_compression_t
DUMP_COMPRESSION_ZSTD,
};


struct plugins_options
{
const char* dump_folder; // PLUGIN_FILEDELETE, PLUGIN_FILEEXTRACTOR
Expand All @@ -154,8 +155,10 @@ struct plugins_options
const char* wow_kernel32_profile; // PLUGIN_ENVMON
const char* iphlpapi_profile; // PLUGIN_ENVMON
const char* mpr_profile; // PLUGIN_ENVMON
const char* syscalls_filter_file; // PLUGIN_SYSCALLS
const char* syscalls_list_file; // PLUGIN_SYSCALLS
bool disable_sysret; // PLUGIN_SYSCALLS
bool syscalls_dereference_args = false; // PLUGIN_SYSCALLS
bool syscalls_nested_args = false; // PLUGIN_SYSCALLS
bool abort_on_bsod; // PLUGIN_BSODMON
const char* crashdump_dir; // PLUGIN_BSODMON
const char* ntdll_profile; // PLUGIN_LIBRARYMON
Expand Down
Loading
Loading