diff --git a/etw_listener.cpp b/etw_listener.cpp index f186597..f7fab93 100644 --- a/etw_listener.cpp +++ b/etw_listener.cpp @@ -60,6 +60,7 @@ struct ProceesStat }; ProceesStat procStats[MAX_PROCESSES] = { 0 }; +time_t g_initTime = 0; // ETW Handler // To filter our events, we want to compare against the @@ -159,7 +160,7 @@ bool isAllocationExecutable(std::uint32_t pid, LPVOID baseAddress) } -inline std::wstring getProcessName(DWORD pid) +inline std::wstring getProcessName(const DWORD pid) { WCHAR processName[MAX_PATH] = { 0 }; if (!process_util::get_process_path(pid, processName, MAX_PATH * 2)) { @@ -175,55 +176,24 @@ inline std::wstring getProcessName(DWORD pid) } -bool isWatchedPid(DWORD pid) +bool isWatchedPid(const DWORD pid) { - if (!g_hh_args.names_list.size() && !g_hh_args.pids_list.size() - && !g_hh_args.ignored_names_list.size()) - { - // no filter applied, watch everything - return true; - } - if (g_hh_args.pids_list.find(pid) != g_hh_args.pids_list.end()) { - // the PID is on the watch list - return true; - } - // get process name: - std::wstring wImgFileName = getProcessName(pid); - if (g_hh_args.names_list.find(wImgFileName) != g_hh_args.names_list.end()) { - // the name is on the watch list + const std::wstring wImgFileName = getProcessName(pid); + const t_single_scan_status res = HHScanner::shouldScanProcess(g_hh_args, g_initTime, pid, wImgFileName.c_str()); + if (res == SSCAN_READY) { return true; } - if (g_hh_args.ignored_names_list.size() && - g_hh_args.ignored_names_list.find(wImgFileName) == g_hh_args.ignored_names_list.end()) - { - // the name is NOT on the ignore list - return true; - } - // the PID is not on the watch list return false; } -bool isWatchedName(std::string& imgFileName) +bool isWatchedName(const std::string& imgFileName) { - if (!g_hh_args.names_list.size() && !g_hh_args.pids_list.size() - && !g_hh_args.ignored_names_list.size()) - { - // no filter applied, watch everything - return true; - } - std::wstring wImgFileName(imgFileName.begin(), imgFileName.end()); - if (g_hh_args.names_list.find(wImgFileName) != g_hh_args.names_list.end()) { - // the name is on the watch list - return true; - } - if (g_hh_args.ignored_names_list.size() && - g_hh_args.ignored_names_list.find(wImgFileName) == g_hh_args.ignored_names_list.end()) - { - // the name is NOT on the ignore list + const std::wstring wImgFileName(imgFileName.begin(), imgFileName.end()); + const t_single_scan_status res = HHScanner::shouldScanProcess(g_hh_args, g_initTime, 0, wImgFileName.c_str()); + if (res == SSCAN_READY) { return true; } - // the name is not on the watch list return false; } @@ -234,7 +204,7 @@ void runHHinNewThread(t_hh_params args) return; } long pid = *(args.pids_list.begin()); - HHScanner hhunter(args); + HHScanner hhunter(args, g_initTime); HHScanReport* report = hhunter.scan(); if (report) { @@ -315,6 +285,7 @@ std::string ipv4FromDword(DWORD ip_dword) bool ETWstart() { krabs::kernel_trace trace(L"HollowsHunter"); + g_initTime = time(NULL); krabs::kernel::process_provider processProvider; krabs::kernel::image_load_provider imageLoadProvider; diff --git a/hh_params.h b/hh_params.h index 4b5c97a..9b4c99f 100644 --- a/hh_params.h +++ b/hh_params.h @@ -31,5 +31,3 @@ typedef struct hh_params } t_hh_params; - - diff --git a/hh_scanner.cpp b/hh_scanner.cpp index 38f0762..cde4b06 100644 --- a/hh_scanner.cpp +++ b/hh_scanner.cpp @@ -80,10 +80,9 @@ namespace files_util { namespace util { - bool is_searched_name(const WCHAR* processName, std::set &names_list) + bool is_searched_name(const WCHAR* processName, const std::set &names_list) { - std::set::iterator itr; - for (itr = names_list.begin(); itr != names_list.end(); ++itr) { + for (auto itr = names_list.begin(); itr != names_list.end(); ++itr) { const WCHAR* searchedName = itr->c_str(); if (_wcsicmp(processName, searchedName) == 0) { return true; @@ -92,7 +91,7 @@ namespace util { return false; } - bool is_searched_pid(long pid, std::set &pids_list) + bool is_searched_pid(long pid, const std::set &pids_list) { std::set::iterator found = pids_list.find(pid); if (found != pids_list.end()) { @@ -102,7 +101,7 @@ namespace util { } template - std::string list_to_str(std::set &list) + std::string list_to_str(const std::set &list) { std::wstringstream stream; @@ -121,10 +120,12 @@ namespace util { //---- -HHScanner::HHScanner(t_hh_params &_args) - : hh_args(_args) +HHScanner::HHScanner(t_hh_params& _args, time_t _initTime) + : hh_args(_args), initTime(_initTime) { - initTime = time(NULL); + if (!initTime) { + initTime = time(NULL); + } isScannerWow64 = process_util::is_wow_64(GetCurrentProcess()); } @@ -151,18 +152,26 @@ void HHScanner::initOutDir(time_t scan_time, pesieve::t_params &pesieve_args) } } -void HHScanner::printScanRoundStats(size_t found, size_t ignored_count) +void HHScanner::printScanRoundStats(size_t found, size_t ignored_count, size_t not_matched_count) { +#ifdef _DEBUG + if (!found && not_matched_count) { + if (!hh_args.quiet) { + const std::lock_guard stdOutLock(g_stdOutMutex); + std::cout << "[WARNING] Some processes were filtered out basing on the defined criteria: " << not_matched_count << " skipped" << std::endl; + } + } +#endif if (!found && hh_args.names_list.size() > 0) { if (!hh_args.quiet) { const std::lock_guard stdOutLock(g_stdOutMutex); - std::cout << "[WARNING] No process from the list: {" << util::list_to_str(hh_args.names_list) << "} was found!" << std::endl; + std::cout << "[WARNING] No process from the list: {" << util::list_to_str(hh_args.names_list) << "} was scanned!" << std::endl; } } if (!found && hh_args.pids_list.size() > 0) { if (!hh_args.quiet) { const std::lock_guard stdOutLock(g_stdOutMutex); - std::cout << "[WARNING] No process from the list: {" << util::list_to_str(hh_args.pids_list) << "} was found!" << std::endl; + std::cout << "[WARNING] No process from the list: {" << util::list_to_str(hh_args.pids_list) << "} was scanned!" << std::endl; } } if (ignored_count > 0) { @@ -180,6 +189,7 @@ size_t HHScanner::scanProcesses(HHScanReport &my_report) size_t count = 0; size_t scanned_count = 0; size_t ignored_count = 0; + size_t filtered_count = 0; HANDLE hProcessSnapShot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); if (hProcessSnapShot == INVALID_HANDLE_VALUE) { @@ -203,6 +213,7 @@ size_t HHScanner::scanProcesses(HHScanReport &my_report) // scan callback const t_single_scan_status stat = scanNextProcess(pe32.th32ProcessID, pe32.szExeFile, my_report); if (stat == SSCAN_IGNORED) ignored_count++; + if (stat == SSCAN_NOT_MATCH) filtered_count++; if (stat == SSCAN_SUCCESS) scanned_count++; count++; @@ -211,7 +222,7 @@ size_t HHScanner::scanProcesses(HHScanReport &my_report) //close the handles CloseHandle(hProcessSnapShot); - printScanRoundStats(scanned_count, ignored_count); + printScanRoundStats(scanned_count, ignored_count, filtered_count); return count; } @@ -257,12 +268,9 @@ void HHScanner::printSingleReport(pesieve::t_report& report) } } -t_single_scan_status HHScanner::scanNextProcess(DWORD pid, WCHAR* exe_file, HHScanReport &my_report) +t_single_scan_status HHScanner::shouldScanProcess(const hh_params &hh_args, const time_t hh_initTime, const DWORD pid, const WCHAR* exe_file) { bool found = false; - - const bool is_process_wow64 = process_util::is_wow_64_by_pid(pid); - const bool check_time = (hh_args.ptimes != TIME_UNDEFINED) ? true : false; #ifdef _DEBUG if (check_time) { @@ -277,8 +285,8 @@ t_single_scan_status HHScanner::scanNextProcess(DWORD pid, WCHAR* exe_file, HHSc if (process_time == INVALID_TIME) return SSCAN_ERROR0; //skip process if cannot retrieve the time // if HH was started after the process - if (this->initTime > process_time) { - time_diff = this->initTime - process_time; + if (hh_initTime > process_time) { + time_diff = hh_initTime - process_time; if (time_diff > hh_args.ptimes) return SSCAN_NOT_MATCH; // skip process created before the supplied time } } @@ -295,6 +303,16 @@ t_single_scan_status HHScanner::scanNextProcess(DWORD pid, WCHAR* exe_file, HHSc return SSCAN_IGNORED; } } + return SSCAN_READY; +} + +t_single_scan_status HHScanner::scanNextProcess(DWORD pid, WCHAR* exe_file, HHScanReport &my_report) +{ + const bool is_process_wow64 = process_util::is_wow_64_by_pid(pid); + t_single_scan_status res = HHScanner::shouldScanProcess(hh_args, this->initTime, pid, exe_file); + if (res != SSCAN_READY) { + return res; + } if (!hh_args.quiet) { const std::lock_guard stdOutLock(g_stdOutMutex); std::cout << ">> Scanning PID: " << std::setw(PID_FIELD_SIZE) << std::dec << pid; @@ -303,9 +321,6 @@ t_single_scan_status HHScanner::scanNextProcess(DWORD pid, WCHAR* exe_file, HHSc if (is_process_wow64) { std::cout << " : 32b"; } - if (check_time) { - std::cout << " : " << time_diff << "s"; - } std::cout << std::endl; } //perform the scan: diff --git a/hh_scanner.h b/hh_scanner.h index 3082d4c..1e74b26 100644 --- a/hh_scanner.h +++ b/hh_scanner.h @@ -17,22 +17,24 @@ typedef enum single_status { SSCAN_ERROR0 = (-1), SSCAN_NOT_MATCH = 0, SSCAN_IGNORED = 1, - SSCAN_SUCCESS = 2 + SSCAN_SUCCESS = 2, + SSCAN_READY = 3 } t_single_scan_status; class HHScanner { public: // is the scanner best suited for the OS bitness static bool isScannerCompatibile(); + static t_single_scan_status shouldScanProcess(const hh_params& hh_args, const time_t hh_initTime, const DWORD pid, const WCHAR* exe_file); - HHScanner(t_hh_params &_args); + HHScanner(t_hh_params& _args, time_t _initTime = 0); HHScanReport* scan(); bool writeToLog(HHScanReport* hh_report); void summarizeScan(HHScanReport *hh_report, bool suspiciousOnly = true); protected: - void printScanRoundStats(size_t found, size_t ignored_count); + void printScanRoundStats(size_t found, size_t ignored_count, size_t not_matched_count); size_t scanProcesses(HHScanReport &my_report); void printSingleReport(pesieve::t_report& report); diff --git a/hh_ver_short.h b/hh_ver_short.h index 7b0613e..892f53e 100644 --- a/hh_ver_short.h +++ b/hh_ver_short.h @@ -3,6 +3,6 @@ #define HH_MAJOR_VERSION 0 #define HH_MINOR_VERSION 3 #define HH_MICRO_VERSION 9 -#define HH_PATCH_VERSION 5 +#define HH_PATCH_VERSION 7 -#define HH_VERSION_STR "0.3.9.5" +#define HH_VERSION_STR "0.3.9.7" diff --git a/pe-sieve b/pe-sieve index 5ccf524..8b5de3b 160000 --- a/pe-sieve +++ b/pe-sieve @@ -1 +1 @@ -Subproject commit 5ccf524018f5de6eccf84f5b5332796408a09783 +Subproject commit 8b5de3b25103ca54136f6a66f256288e6ebc2354