Advertisement
alien_fx_fiend

PE-Explorer GUI (Ctrl+O OpenFile Hotkey) *FINAL RELEASE 2.9*

Nov 27th, 2024
58
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 57.88 KB | Source Code | 0 0
  1. ==++ Here's the full source code for (file 1/1) "main.cpp":: ++==
  2. #define STRICT
  3. #define WIN32_LEAN_AND_MEAN
  4. #include <Windows.h>
  5. #include <winternl.h>
  6. #include <CommCtrl.h>
  7. #include <commdlg.h>
  8. #include <string>
  9. #include <strsafe.h>
  10. #include <sstream>
  11. #include <iomanip>
  12. #include <stdio.h>
  13. #include <vector>
  14. #include <shellapi.h>
  15. //#include "helpers.h"
  16. #include "resource.h"
  17. #pragma comment(lib, "comctl32.lib")
  18.  
  19. namespace PEHelpers {
  20.    std::wstring GetImageCharacteristics(DWORD characteristics) {
  21.        if (characteristics & IMAGE_FILE_DLL) return L"(DLL)";
  22.        if (characteristics & IMAGE_FILE_SYSTEM) return L"(DRIVER)";
  23.        if (characteristics & IMAGE_FILE_EXECUTABLE_IMAGE) return L"(EXE)";
  24.        return L"(UNKNOWN)";
  25.    }
  26.  
  27.    std::wstring GetSubsystem(WORD subsystem) {
  28.        switch (subsystem) {
  29.        case IMAGE_SUBSYSTEM_NATIVE: return L"(NATIVE/DRIVER)";
  30.        case IMAGE_SUBSYSTEM_WINDOWS_GUI: return L"(GUI)";
  31.        case IMAGE_SUBSYSTEM_WINDOWS_CUI: return L"(CONSOLE)";
  32.        default: return L"(UNKNOWN)";
  33.        }
  34.    }
  35.  
  36.    std::wstring GetDataDirectoryName(int DirectoryNumber) {
  37.        switch (DirectoryNumber) {
  38.        case 0: return L"Export Table";
  39.        case 1: return L"Import Table";
  40.        case 2: return L"Resource Table";
  41.        case 3: return L"Exception Entry";
  42.        case 4: return L"Security Entry";
  43.        case 5: return L"Relocation Table";
  44.        case 6: return L"Debug Entry";
  45.        case 7: return L"Copyright Entry";
  46.        case 8: return L"Global PTR Entry";
  47.        case 9: return L"TLS Entry";
  48.        case 10: return L"Configuration Entry";
  49.        case 11: return L"Bound Import Entry";
  50.        case 12: return L"IAT";
  51.        case 13: return L"Delay Import Descriptor";
  52.        case 14: return L"COM Descriptor";
  53.        default: return L"Unknown";
  54.        }
  55.    }
  56.  
  57.    std::wstring GetSectionProtection(DWORD characteristics) {
  58.        std::wstring protection = L"(";
  59.        bool needsSeparator = false;
  60.  
  61.        if (characteristics & IMAGE_SCN_MEM_EXECUTE) {
  62.            protection += L"EXECUTE";
  63.            needsSeparator = true;
  64.        }
  65.  
  66.        if (characteristics & IMAGE_SCN_MEM_READ) {
  67.            if (needsSeparator) protection += L" | ";
  68.            protection += L"READ";
  69.            needsSeparator = true;
  70.        }
  71.  
  72.        if (characteristics & IMAGE_SCN_MEM_WRITE) {
  73.            if (needsSeparator) protection += L" | ";
  74.            protection += L"WRITE";
  75.        }
  76.  
  77.        protection += L")";
  78.        return protection;
  79.    }
  80.  
  81.    PIMAGE_SECTION_HEADER GetExportSection(const PIMAGE_SECTION_HEADER pImageSectionHeader,
  82.        const int NumberOfSections,
  83.        const DWORD_PTR dExportAddress) {
  84.        for (int i = 0; i < NumberOfSections; ++i) {
  85.            const auto pCurrentSectionHeader =
  86.                (PIMAGE_SECTION_HEADER)((DWORD_PTR)pImageSectionHeader + i * sizeof(IMAGE_SECTION_HEADER));
  87.  
  88.            if (dExportAddress >= pCurrentSectionHeader->VirtualAddress &&
  89.                dExportAddress < pCurrentSectionHeader->VirtualAddress + pCurrentSectionHeader->Misc.VirtualSize)
  90.                return pCurrentSectionHeader;
  91.        }
  92.        return nullptr;
  93.    }
  94. }
  95.  
  96. using namespace std;
  97.  
  98. // At the top of your file, change the window class name to wide string
  99. #define WINDOW_CLASS_NAME L"PEAnalyzerWindow"
  100. //const wchar_t* const WINDOW_CLASS_NAME = L"PEAnalyzerWindow";
  101.  
  102. // Use ANSI versions explicitly
  103. //#undef CreateWindow
  104. //#undef CreateWindowEx
  105. //#define CreateWindow  CreateWindowW
  106. //#define CreateWindowEx CreateWindowExW
  107.  
  108. // Helper function to replace printf with GUI output
  109. #define OUTPUT(format, ...) AppendToOutput(L##format, ##__VA_ARGS__)
  110. //#define OUTPUT(format, ...) AppendToOutput(format, ##__VA_ARGS__)
  111. //#define printf(format, ...) AppendToOutput(format, ##__VA_ARGS__)
  112.  
  113. // Window dimensions
  114. #define WINDOW_WIDTH    1024
  115. #define WINDOW_HEIGHT   768
  116. #define EDIT_MARGIN    10
  117.  
  118. // Global variables
  119. HWND g_hMainWindow = NULL;
  120. HWND g_hEditControl = NULL;
  121. HFONT g_hFont = NULL;
  122. std::wstringstream g_OutputText;
  123. WCHAR filePathW[MAX_PATH];
  124. std::vector<wchar_t> g_OutputBuffer;
  125. std::wstring tempBuffer; // Declare tempBuffer globally
  126. HWND g_hStatusBar = NULL;
  127.  
  128. // Function declarations
  129. LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
  130. LRESULT CALLBACK EditSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData);
  131. void CreateMainWindow(HINSTANCE hInstance);
  132. void InitializeControls(HWND hwnd);
  133. void AddMenus(HWND hwnd);
  134. void OpenFileDialog(HWND hwnd);
  135. //void AnalyzePEFile(const WCHAR* filePathW);
  136. void AnalyzePEFile(const wchar_t* filePathW);
  137. HANDLE GetFileContent(const wchar_t* lpFilePath);
  138. /*void GetDataDirectories(PIMAGE_DATA_DIRECTORY pImageDataDirectory);
  139. PIMAGE_SECTION_HEADER GetSections(const PIMAGE_SECTION_HEADER pImageSectionHeader,
  140.    int NumberOfSections, DWORD dImportAddress);
  141. void GetImports32(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor,
  142.    DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection);
  143. void GetImports64(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor,
  144.    DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection);*/
  145. void AppendToOutput(const wchar_t* format, ...);
  146. void UpdateEditControl();
  147.  
  148. // Main window class name
  149. //const char* const WINDOW_CLASS_NAME = "PEAnalyzerWindow";
  150.  
  151. int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
  152.    INITCOMMONCONTROLSEX icc = { sizeof(INITCOMMONCONTROLSEX), ICC_WIN95_CLASSES };
  153.    InitCommonControlsEx(&icc);
  154.  
  155.    // Get command line parameters in Unicode
  156.    int argc;
  157.    LPWSTR* argv = CommandLineToArgvW(GetCommandLineW(), &argc);
  158.  
  159.    CreateMainWindow(hInstance);
  160.    if (!g_hMainWindow) {
  161.        LocalFree(argv);
  162.        return -1;
  163.    }
  164.  
  165.    ShowWindow(g_hMainWindow, nCmdShow);
  166.    UpdateWindow(g_hMainWindow);
  167.  
  168.    // If there's a command line parameter, process it
  169.     if (argc > 1) {
  170.         // Process the first parameter as file path
  171.         SetWindowTextW(g_hEditControl, L"");
  172.         g_OutputText.str(L"");
  173.         g_OutputText.clear();
  174.         AnalyzePEFile(argv[1]);
  175.         UpdateEditControl();
  176.     }
  177.  
  178.     LocalFree(argv);
  179.  
  180.     MSG msg = {};
  181.     while (GetMessage(&msg, NULL, 0, 0)) {
  182.         TranslateMessage(&msg);
  183.         DispatchMessage(&msg);
  184.     }
  185.  
  186.     if (g_hFont) DeleteObject(g_hFont);
  187.     return (int)msg.wParam;
  188. }
  189.  
  190. void CreateMainWindow(HINSTANCE hInstance) {
  191.     WNDCLASSEXW wc = { sizeof(WNDCLASSEXW), 0, WindowProc, 0, 0, hInstance,
  192.         LoadIcon(hInstance, MAKEINTRESOURCE(IDI_ICON1)),
  193.         LoadCursor(NULL, IDC_ARROW),
  194.         (HBRUSH)(COLOR_WINDOW + 1),
  195.         NULL, WINDOW_CLASS_NAME,
  196.         LoadIcon(hInstance, MAKEINTRESOURCE(IDI_ICON1)) };
  197.     RegisterClassExW(&wc);
  198.  
  199.     // Get screen dimensions
  200.     int screenWidth = GetSystemMetrics(SM_CXSCREEN);
  201.     int screenHeight = GetSystemMetrics(SM_CYSCREEN);
  202.  
  203.     // Calculate center position
  204.     int windowX = (screenWidth - WINDOW_WIDTH) / 2;
  205.     int windowY = (screenHeight - WINDOW_HEIGHT) / 2;
  206.  
  207.     // Remove WS_MAXIMIZEBOX and WS_THICKFRAME from the window style
  208.     DWORD style = (WS_OVERLAPPEDWINDOW & ~WS_MAXIMIZEBOX) & ~WS_THICKFRAME;
  209.     //WS_OVERLAPPEDWINDOW ~~> style
  210.     g_hMainWindow = CreateWindowExW(0, WINDOW_CLASS_NAME, L"PE File Analyzer",
  211.         style, windowX, windowY, WINDOW_WIDTH, WINDOW_HEIGHT,
  212.         nullptr, nullptr, hInstance, nullptr);
  213. }
  214.  
  215. void InitializeControls(HWND hwnd) {
  216.     // Create Status Bar
  217.     g_hStatusBar = CreateWindowEx(0, STATUSCLASSNAME, NULL,
  218.         WS_CHILD | WS_VISIBLE | SBARS_SIZEGRIP,
  219.         0, 0, 0, 0, hwnd, NULL,
  220.         (HINSTANCE)GetWindowLongPtr(hwnd, GWLP_HINSTANCE), NULL);
  221.  
  222.     // Get status bar height
  223.     RECT rcStatus;
  224.     GetWindowRect(g_hStatusBar, &rcStatus);
  225.     int statusHeight = rcStatus.bottom - rcStatus.top;
  226.  
  227.     // Create Edit Control with adjusted height
  228.     RECT rcClient;
  229.     GetClientRect(hwnd, &rcClient);
  230.     g_hEditControl = CreateWindowExW(WS_EX_CLIENTEDGE, L"EDIT", L"",
  231.         WS_CHILD | WS_VISIBLE | WS_VSCROLL | WS_HSCROLL |
  232.         ES_MULTILINE | ES_AUTOVSCROLL | ES_AUTOHSCROLL,
  233.         EDIT_MARGIN, EDIT_MARGIN,
  234.         rcClient.right - (2 * EDIT_MARGIN),
  235.         rcClient.bottom - statusHeight - (2 * EDIT_MARGIN),
  236.         hwnd, nullptr,
  237.         (HINSTANCE)GetWindowLongPtr(hwnd, GWLP_HINSTANCE), nullptr);
  238.  
  239.     g_hFont = CreateFont(-14, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0,
  240.         ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS,
  241.         DEFAULT_QUALITY, DEFAULT_PITCH | FF_MODERN, L"Consolas");
  242.  
  243.     if (g_hFont)
  244.         SendMessage(g_hEditControl, WM_SETFONT, (WPARAM)g_hFont, TRUE);
  245.  
  246.     // Add this line to subclass the Edit control
  247.     SetWindowSubclass(g_hEditControl, EditSubclassProc, 0, 0);
  248. }
  249.  
  250. void AddMenus(HWND hwnd) {
  251.     HMENU hMenuBar = CreateMenu();
  252.     HMENU hFileMenu = CreateMenu();
  253.     AppendMenu(hMenuBar, MF_POPUP, (UINT_PTR)hFileMenu, L"&File");
  254.     AppendMenu(hFileMenu, MF_STRING, 1, L"&Open\tCtrl+O");  // Updated to show shortcut
  255.     AppendMenu(hFileMenu, MF_STRING, 2, L"E&xit");
  256.     SetMenu(hwnd, hMenuBar);
  257. }
  258.  
  259. LRESULT CALLBACK EditSubclassProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) {
  260.     if (uMsg == WM_KEYDOWN) {
  261.         // Check for Ctrl+O
  262.         if ((GetKeyState(VK_CONTROL) & 0x8000) && wParam == 'O') {
  263.             SendMessage(GetParent(hwnd), WM_COMMAND, 1, 0);  // Send the Open command
  264.             return 0;
  265.         }
  266.  
  267.         // Existing cases
  268.         switch (wParam) {
  269.         case VK_F1:
  270.             SendMessage(GetParent(hwnd), WM_KEYDOWN, VK_F1, 0);
  271.             return 0;
  272.         case VK_ESCAPE:
  273.             SendMessage(GetParent(hwnd), WM_KEYDOWN, VK_ESCAPE, 0);
  274.             return 0;
  275.         }
  276.     }
  277.     return DefSubclassProc(hwnd, uMsg, wParam, lParam);
  278. }
  279.  
  280. LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {
  281.     switch (uMsg) {
  282.     case WM_CREATE: InitializeControls(hwnd); AddMenus(hwnd); return 0;
  283.     case WM_SIZE:
  284.     {
  285.         RECT rcClient;
  286.         GetClientRect(hwnd, &rcClient);
  287.  
  288.         // Resize status bar (it will auto-adjust its height)
  289.         SendMessage(g_hStatusBar, WM_SIZE, 0, 0);
  290.  
  291.         // Get status bar height
  292.         RECT rcStatus;
  293.         GetWindowRect(g_hStatusBar, &rcStatus);
  294.         int statusHeight = rcStatus.bottom - rcStatus.top;
  295.  
  296.         // Resize edit control
  297.         SetWindowPos(g_hEditControl, NULL,
  298.             EDIT_MARGIN,
  299.             EDIT_MARGIN,
  300.             rcClient.right - (2 * EDIT_MARGIN),
  301.             rcClient.bottom - statusHeight - (2 * EDIT_MARGIN),
  302.             SWP_NOZORDER);
  303.     }
  304.     return 0;
  305.     case WM_KEYDOWN:
  306.     {
  307.         // Check if Ctrl is pressed
  308.         if (GetKeyState(VK_CONTROL) & 0x8000) {
  309.             switch (wParam) {
  310.             case 'O':  // Ctrl+O
  311.                 OpenFileDialog(hwnd);
  312.                 return 0;
  313.             }
  314.         }
  315.  
  316.         // Keep your existing VK_F1 and VK_ESCAPE handling
  317.         switch (wParam) {
  318.         case VK_F1:
  319.             MessageBoxW(hwnd,
  320.                 L"PE Header Parser 2.9 GUI-based Programmed in C++ Win32 API (1369 lines of code) by Entisoft Software(c) Evans Thorpemorton",
  321.                 L"About",
  322.                 MB_OK | MB_ICONINFORMATION);
  323.             return 0;
  324.         case VK_ESCAPE:
  325.             PostQuitMessage(0);
  326.             return 0;
  327.         }
  328.     }
  329.     break;
  330.     case WM_COMMAND: if (LOWORD(wParam) == 1) OpenFileDialog(hwnd); if (LOWORD(wParam) == 2) PostQuitMessage(0); return 0;
  331.     case WM_DESTROY:
  332.         if (g_hStatusBar) DestroyWindow(g_hStatusBar);
  333.         PostQuitMessage(0);
  334.         return 0;
  335.     }
  336.     return DefWindowProc(hwnd, uMsg, wParam, lParam);
  337. }
  338.  
  339. void SetStatusText(const wchar_t* text) {
  340.     SendMessage(g_hStatusBar, SB_SETTEXT, 0, (LPARAM)text);
  341. }
  342.  
  343. void ShowProgress(int percentage) {
  344.     wchar_t status[256];
  345.     swprintf_s(status, L"Analyzing... %d%%", percentage);
  346.     SetStatusText(status);
  347. }
  348.  
  349. void OpenFileDialog(HWND hwnd) {
  350.     WCHAR fileName[MAX_PATH] = L"";
  351.     OPENFILENAMEW ofn = { sizeof(OPENFILENAMEW), hwnd, NULL, L"Executable Files (*.exe;*.dll)\0*.exe;*.dll\0All Files (*.*)\0*.*\0", NULL, 0, 1, fileName, MAX_PATH, NULL, 0, NULL, NULL, OFN_EXPLORER | OFN_FILEMUSTEXIST | OFN_HIDEREADONLY, 0, 0, L"exe", NULL, NULL, NULL };
  352.     if (GetOpenFileNameW(&ofn)) {
  353.         SetWindowTextW(g_hEditControl, L"");
  354.         g_OutputText.str(L"");
  355.         g_OutputText.clear();
  356.         AnalyzePEFile(ofn.lpstrFile);
  357.         UpdateEditControl();
  358.     }
  359. }
  360.  
  361. class FileMapper {
  362. private:
  363.     HANDLE hFile = INVALID_HANDLE_VALUE;
  364.     HANDLE hMapping = nullptr;
  365.     LPVOID lpView = nullptr;
  366.  
  367. public:
  368.     ~FileMapper() {
  369.         if (lpView) UnmapViewOfFile(lpView);
  370.         if (hMapping) CloseHandle(hMapping);
  371.         if (hFile != INVALID_HANDLE_VALUE) CloseHandle(hFile);
  372.     }
  373.  
  374.     bool Initialize(const wchar_t* path) {
  375.         hFile = CreateFileW(path, GENERIC_READ, FILE_SHARE_READ, nullptr,
  376.             OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, nullptr);
  377.         if (hFile == INVALID_HANDLE_VALUE) return false;
  378.  
  379.         hMapping = CreateFileMappingW(hFile, nullptr, PAGE_READONLY, 0, 0, nullptr);
  380.         if (!hMapping) return false;
  381.  
  382.         lpView = MapViewOfFile(hMapping, FILE_MAP_READ, 0, 0, 0);
  383.         return lpView != nullptr;
  384.     }
  385.  
  386.     LPVOID GetView() const { return lpView; }
  387. };
  388.  
  389. // Modified AppendToOutput to handle newlines properly:
  390. void AppendToOutput(const wchar_t* format, ...) {
  391.     std::vector<wchar_t> buffer(1024);
  392.     va_list args;
  393.     va_start(args, format);
  394.  
  395.     while (true) {
  396.         int result = _vsnwprintf(buffer.data(), buffer.size(), format, args);
  397.         if (result >= 0) break;
  398.         buffer.resize(buffer.size() * 2);
  399.     }
  400.     va_end(args);
  401.  
  402.     // Convert \n to \r\n
  403.     std::wstring output = buffer.data();
  404.     size_t pos = 0;
  405.     while ((pos = output.find(L'\n', pos)) != std::wstring::npos) {
  406.         if (pos == 0 || output[pos - 1] != L'\r') {
  407.             output.insert(pos, L"\r");
  408.             pos += 2;
  409.         }
  410.         else {
  411.             pos++;
  412.         }
  413.     }
  414.  
  415.     g_OutputText << output;
  416.     UpdateEditControl();
  417. }
  418.  
  419. /*
  420. void AppendToOutput(const wchar_t* format, ...) {
  421.     wchar_t buffer[16384]; // Ensure sufficient buffer size
  422.     va_list args;
  423.     va_start(args, format);
  424.     StringCchVPrintfW(buffer, ARRAYSIZE(buffer), format, args);
  425.     va_end(args);
  426.  
  427.     tempBuffer += buffer;
  428.  
  429.     // Update Edit Control periodically to improve performance
  430.     if (tempBuffer.size() > 8000) {
  431.         g_OutputText << tempBuffer;
  432.         tempBuffer.clear();
  433.  
  434.         SetWindowTextW(g_hEditControl, g_OutputText.str().c_str());
  435.         SendMessage(g_hEditControl, EM_SETSEL, -1, -1);
  436.         SendMessage(g_hEditControl, EM_SCROLLCARET, 0, 0);
  437.     }
  438. }
  439.  
  440.  
  441. // Final update to flush any remaining content
  442. void FlushOutput() {
  443.     if (!tempBuffer.empty()) {
  444.         g_OutputText << tempBuffer;
  445.         tempBuffer.clear();
  446.  
  447.         SetWindowTextW(g_hEditControl, g_OutputText.str().c_str());
  448.         SendMessage(g_hEditControl, EM_SETSEL, -1, -1);
  449.         SendMessage(g_hEditControl, EM_SCROLLCARET, 0, 0);
  450.     }
  451. }
  452. */
  453.  
  454.  
  455. /*
  456. //use below ^^ ALWAYS
  457. void AppendToOutput(const wchar_t* format, ...) {
  458.     va_list args;
  459.     va_start(args, format);
  460.  
  461.     // Use a vector as a dynamically resizable buffer
  462.     std::vector<wchar_t> buffer(16384); // Start with an initial size
  463.     int result = -1;
  464.  
  465.     while (true) {
  466.         // Attempt to format the string
  467.         result = _vsnwprintf(buffer.data(), buffer.size(), format, args);
  468.  
  469.         if (result >= 0 && static_cast<size_t>(result) < buffer.size()) {
  470.             // Successfully formatted within the current buffer size
  471.             break;
  472.         }
  473.  
  474.         // Resize the buffer and try again
  475.         buffer.resize(buffer.size() * 2);
  476.     }
  477.     va_end(args);
  478.  
  479.     // Convert `\n` to `\r\n` for proper display in the EditBox
  480.     std::wstring formattedOutput(buffer.data());
  481.     size_t pos = 0;
  482.     while ((pos = formattedOutput.find(L'\n', pos)) != std::wstring::npos) {
  483.         formattedOutput.replace(pos, 1, L"\r\n");
  484.         pos += 2; // Move past the replacement
  485.     }
  486.  
  487.     // Append to the global output buffer
  488.     g_OutputText << formattedOutput;
  489.  
  490.     // Update the EditBox periodically to prevent overloading
  491.     if (g_OutputText.str().size() > 8000) {
  492.         SetWindowTextW(g_hEditControl, g_OutputText.str().c_str());
  493.         SendMessage(g_hEditControl, EM_SETSEL, -1, -1);
  494.         SendMessage(g_hEditControl, EM_SCROLLCARET, 0, 0);
  495.     }
  496. }
  497. //use above ^^ ALWAYS
  498. */
  499.  
  500. //currentlatest
  501. /*void AppendToOutput(const wchar_t* format, ...) {
  502.     wchar_t buffer[4096];
  503.     va_list args;
  504.     va_start(args, format);
  505.     StringCchVPrintfW(buffer, ARRAYSIZE(buffer), format, args);
  506.     va_end(args);
  507.     g_OutputText << buffer;
  508.     SetWindowTextW(g_hEditControl, g_OutputText.str().c_str());
  509.     SendMessage(g_hEditControl, EM_SETSEL, -1, -1);
  510.     SendMessage(g_hEditControl, EM_SCROLLCARET, 0, 0);
  511. }
  512. */
  513.  
  514. //use-below-basic-failsafe-working vv
  515. //basic test function
  516. /*void AnalyzePEFile(const wchar_t* filePathW) {
  517.     OUTPUT("[+] Analyzing file: %s\n", filePathW);
  518.     LPVOID lpFileContent = GetFileContent(filePathW);
  519.     if (!lpFileContent) { OUTPUT("[-] Could not read file.\n"); return; }
  520.     PIMAGE_DOS_HEADER dosHeader = (PIMAGE_DOS_HEADER)lpFileContent;
  521.     if (dosHeader->e_magic != IMAGE_DOS_SIGNATURE) { OUTPUT("[-] Invalid DOS signature.\n"); HeapFree(GetProcessHeap(), 0, lpFileContent); return; }
  522.     PIMAGE_NT_HEADERS ntHeaders = (PIMAGE_NT_HEADERS)((DWORD_PTR)lpFileContent + dosHeader->e_lfanew);
  523.     if (ntHeaders->Signature != IMAGE_NT_SIGNATURE) { OUTPUT("[-] Invalid NT signature.\n"); HeapFree(GetProcessHeap(), 0, lpFileContent); return; }
  524.     OUTPUT("[+] PE file analyzed successfully.\n");
  525.     HeapFree(GetProcessHeap(), 0, lpFileContent);
  526.     UpdateEditControl();
  527. }*/
  528. //use-above-basic-failsafe-working vv
  529.  
  530. //use vectors for unlimited size growth of buffer, use an alternative to editbox, check for fast loops overloading, in its primitive form it works properly! try w/o getimports3264 datadirectories getsections
  531.  
  532. void AnalyzePEFile(const wchar_t* filePathW) {
  533.     OUTPUT("[+] Starting PE Analysis for: %s\n\n", filePathW);
  534.  
  535.     FileMapper mapper;
  536.     if (!mapper.Initialize(filePathW)) {
  537.         SetStatusText(L"Failed to open file!");
  538.         OUTPUT("[-] Failed to open file! Error: %d\r\n", GetLastError());
  539.         return;
  540.     }
  541.  
  542.     ShowProgress(20);  // After initial file opening
  543.  
  544.    
  545.     // Open and read file
  546.     HANDLE hFile = CreateFileW(filePathW, GENERIC_READ, FILE_SHARE_READ, nullptr,
  547.         OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, nullptr);
  548.     if (hFile == INVALID_HANDLE_VALUE) {
  549.         OUTPUT("[-] Failed to open file! Error: %d\n", GetLastError());
  550.         return;
  551.     }
  552.  
  553.     DWORD fileSize = GetFileSize(hFile, nullptr);
  554.     if (fileSize == INVALID_FILE_SIZE) {
  555.         CloseHandle(hFile);
  556.         OUTPUT("[-] Failed to get file size! Error: %d\n", GetLastError());
  557.         return;
  558.     }
  559.  
  560.     HANDLE hFileMapping = CreateFileMappingW(hFile, nullptr, PAGE_READONLY, 0, 0, nullptr);
  561.     if (!hFileMapping) {
  562.         CloseHandle(hFile);
  563.         OUTPUT("[-] Failed to create file mapping! Error: %d\n", GetLastError());
  564.         return;
  565.     }
  566.  
  567.     LPVOID lpFileContent = MapViewOfFile(hFileMapping, FILE_MAP_READ, 0, 0, 0);
  568.     if (!lpFileContent) {
  569.         CloseHandle(hFileMapping);
  570.         CloseHandle(hFile);
  571.         OUTPUT("[-] Failed to map view of file! Error: %d\n", GetLastError());
  572.         return;
  573.     }
  574.  
  575.     const auto pImageDosHeader = static_cast<PIMAGE_DOS_HEADER>(mapper.GetView());
  576.     if (pImageDosHeader->e_magic != IMAGE_DOS_SIGNATURE) {
  577.         OUTPUT("[-] Invalid DOS signature!\r\n");
  578.         return;
  579.     }
  580.  
  581.     ShowProgress(40);
  582.  
  583.     const auto pImageNtHeaders = reinterpret_cast<PIMAGE_NT_HEADERS>(
  584.         static_cast<BYTE*>(mapper.GetView()) + pImageDosHeader->e_lfanew);
  585.     if (pImageNtHeaders->Signature != IMAGE_NT_SIGNATURE) {
  586.         OUTPUT("[-] Invalid NT signature!\r\n");
  587.         return;
  588.     }
  589.  
  590.     ShowProgress(60);
  591.  
  592.     // Print File Header Information
  593.     OUTPUT("[+] PE FILE HEADER\n");
  594.     OUTPUT("\tMachine: 0x%X\n", pImageNtHeaders->FileHeader.Machine);
  595.     OUTPUT("\tNumberOfSections: 0x%X\n", pImageNtHeaders->FileHeader.NumberOfSections);
  596.     OUTPUT("\tTimeDateStamp: 0x%X\n", pImageNtHeaders->FileHeader.TimeDateStamp);
  597.     OUTPUT("\tPointerToSymbolTable: 0x%X\r\n",
  598.         static_cast<DWORD>(pImageNtHeaders->FileHeader.PointerToSymbolTable));
  599.     OUTPUT("\tNumberOfSymbols: 0x%X\r\n",
  600.         static_cast<DWORD>(pImageNtHeaders->FileHeader.NumberOfSymbols));
  601.     OUTPUT("\tSizeOfOptionalHeader: 0x%X\r\n",
  602.         static_cast<DWORD>(pImageNtHeaders->FileHeader.SizeOfOptionalHeader));
  603.     OUTPUT("\tCharacteristics: 0x%X %s\n\n",
  604.         pImageNtHeaders->FileHeader.Characteristics,
  605.         PEHelpers::GetImageCharacteristics(pImageNtHeaders->FileHeader.Characteristics).c_str());
  606.  
  607.     // Print Optional Header Information
  608.     OUTPUT("[+] PE OPTIONAL HEADER\n");
  609.     OUTPUT("\tMagic: 0x%X\n", pImageNtHeaders->OptionalHeader.Magic);
  610.     OUTPUT("\tAddressOfEntryPoint: 0x%X\n", pImageNtHeaders->OptionalHeader.AddressOfEntryPoint);
  611.     OUTPUT("\tImageBase: 0x%llX\n", (ULONGLONG)pImageNtHeaders->OptionalHeader.ImageBase);
  612.     OUTPUT("\tSectionAlignment: 0x%X\n", pImageNtHeaders->OptionalHeader.SectionAlignment);
  613.     OUTPUT("\tFileAlignment: 0x%X\n", pImageNtHeaders->OptionalHeader.FileAlignment);
  614.    
  615.     // Added missing Optional Header fields
  616.     OUTPUT("\tMajorOperatingSystemVersion: 0x%X\r\n",
  617.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MajorOperatingSystemVersion));
  618.     OUTPUT("\tMinorOperatingSystemVersion: 0x%X\r\n",
  619.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MinorOperatingSystemVersion));
  620.     OUTPUT("\tMajorImageVersion: 0x%X\r\n",
  621.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MajorImageVersion));
  622.     OUTPUT("\tMinorImageVersion: 0x%X\r\n",
  623.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MinorImageVersion));
  624.     OUTPUT("\tMajorSubsystemVersion: 0x%X\r\n",
  625.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MajorSubsystemVersion));
  626.     OUTPUT("\tMinorSubsystemVersion: 0x%X\r\n",
  627.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.MinorSubsystemVersion));
  628.     OUTPUT("\tWin32VersionValue: 0x%X\r\n",
  629.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.Win32VersionValue));
  630.     OUTPUT("\tSizeOfImage: 0x%X\r\n",
  631.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.SizeOfImage));
  632.     OUTPUT("\tSizeOfHeaders: 0x%X\r\n",
  633.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.SizeOfHeaders));
  634.     OUTPUT("\tCheckSum: 0x%X\r\n",
  635.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.CheckSum));
  636.     OUTPUT("\tSubsystem: 0x%X %s\r\n",
  637.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.Subsystem),
  638.         PEHelpers::GetSubsystem(pImageNtHeaders->OptionalHeader.Subsystem).c_str());
  639.     OUTPUT("\tDllCharacteristics: 0x%X\r\n",
  640.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.DllCharacteristics));
  641.     OUTPUT("\tSizeOfStackReserve: 0x%llX\r\n",
  642.         static_cast<ULONGLONG>(pImageNtHeaders->OptionalHeader.SizeOfStackReserve));
  643.     OUTPUT("\tSizeOfStackCommit: 0x%llX\r\n",
  644.         static_cast<ULONGLONG>(pImageNtHeaders->OptionalHeader.SizeOfStackCommit));
  645.     OUTPUT("\tSizeOfHeapReserve: 0x%llX\r\n",
  646.         static_cast<ULONGLONG>(pImageNtHeaders->OptionalHeader.SizeOfHeapReserve));
  647.     OUTPUT("\tSizeOfHeapCommit: 0x%llX\r\n",
  648.         static_cast<ULONGLONG>(pImageNtHeaders->OptionalHeader.SizeOfHeapCommit));
  649.     OUTPUT("\tLoaderFlags: 0x%X\r\n",
  650.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.LoaderFlags));
  651.     OUTPUT("\tNumberOfRvaAndSizes: 0x%X\r\n\r\n",
  652.         static_cast<DWORD>(pImageNtHeaders->OptionalHeader.NumberOfRvaAndSizes));
  653.    
  654.     OUTPUT("\tSubsystem: 0x%X %s\n\n",
  655.         pImageNtHeaders->OptionalHeader.Subsystem,
  656.         PEHelpers::GetSubsystem(pImageNtHeaders->OptionalHeader.Subsystem).c_str());
  657.  
  658.     // Print Data Directories
  659.     OUTPUT("[+] PE DATA DIRECTORIES\n");
  660.     for (int i = 0; i < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; i++) {
  661.         const auto& dir = pImageNtHeaders->OptionalHeader.DataDirectory[i];
  662.         if (dir.VirtualAddress != 0) {
  663.             OUTPUT("\t%s:\n", PEHelpers::GetDataDirectoryName(i).c_str());
  664.             OUTPUT("\t\tVirtualAddress: 0x%X\n", dir.VirtualAddress);
  665.             OUTPUT("\t\tSize: 0x%X\n", dir.Size);
  666.         }
  667.     }
  668.  
  669.     // Analyze Sections
  670.     OUTPUT("\n[+] PE IMAGE SECTIONS\r\n");
  671.     auto pSection = IMAGE_FIRST_SECTION(pImageNtHeaders);
  672.     for (WORD i = 0; i < pImageNtHeaders->FileHeader.NumberOfSections; i++, pSection++) {
  673.         // Create a null-terminated string from the section name
  674.         char sectionName[IMAGE_SIZEOF_SHORT_NAME + 1] = {};
  675.         memcpy(sectionName, pSection->Name, IMAGE_SIZEOF_SHORT_NAME);
  676.  
  677.         // Remove any non-printable characters
  678.         for (int j = 0; j < IMAGE_SIZEOF_SHORT_NAME; j++) {
  679.             if (!isprint(static_cast<unsigned char>(sectionName[j]))) {
  680.                 sectionName[j] = '\0';
  681.             }
  682.         }
  683.  
  684.         // Convert to wide string
  685.         wchar_t wideSectionName[IMAGE_SIZEOF_SHORT_NAME + 1] = {};
  686.         MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED,
  687.             sectionName, -1,
  688.             wideSectionName, IMAGE_SIZEOF_SHORT_NAME + 1);
  689.  
  690.         OUTPUT("\tSECTION : %s\r\n", wideSectionName);
  691.         OUTPUT("\t\tMisc (PhysicalAddress) : 0x%X\r\n", pSection->Misc.PhysicalAddress);
  692.         OUTPUT("\t\tMisc (VirtualSize) : 0x%X\r\n", pSection->Misc.VirtualSize);
  693.         OUTPUT("\t\tVirtualAddress : 0x%X\r\n", pSection->VirtualAddress);
  694.         OUTPUT("\t\tSizeOfRawData : 0x%X\r\n", pSection->SizeOfRawData);
  695.         OUTPUT("\t\tPointerToRawData : 0x%X\r\n", pSection->PointerToRawData);
  696.         OUTPUT("\t\tPointerToRelocations : 0x%X\r\n", pSection->PointerToRelocations);
  697.         OUTPUT("\t\tPointerToLinenumbers : 0x%X\r\n", pSection->PointerToLinenumbers);
  698.         OUTPUT("\t\tNumberOfRelocations : 0x%X\r\n", pSection->NumberOfRelocations);
  699.         OUTPUT("\t\tNumberOfLinenumbers : 0x%X\r\n", pSection->NumberOfLinenumbers);
  700.         OUTPUT("\t\tCharacteristics : 0x%X %s\r\n\r\n",
  701.             pSection->Characteristics,
  702.             PEHelpers::GetSectionProtection(pSection->Characteristics).c_str());
  703.     }
  704.  
  705.     ShowProgress(80);
  706.  
  707.     // Analyze Imports
  708.     const auto& importDir = pImageNtHeaders->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT];
  709.     if (importDir.VirtualAddress && importDir.Size) {
  710.         OUTPUT("\n[+] IMPORTED DLLS AND FUNCTIONS\r\n");
  711.  
  712.         // Find the section containing imports
  713.         auto pSection = IMAGE_FIRST_SECTION(pImageNtHeaders);
  714.         PIMAGE_SECTION_HEADER pImportSection = nullptr;
  715.  
  716.         // Find the import section
  717.         for (WORD i = 0; i < pImageNtHeaders->FileHeader.NumberOfSections; i++, pSection++) {
  718.             if (importDir.VirtualAddress >= pSection->VirtualAddress &&
  719.                 importDir.VirtualAddress < (pSection->VirtualAddress + pSection->Misc.VirtualSize)) {
  720.                 pImportSection = pSection;
  721.                 break;
  722.             }
  723.         }
  724.  
  725.         if (!pImportSection) {
  726.             OUTPUT("[-] Could not find import section\r\n");
  727.             return;
  728.         }
  729.  
  730.         // Get the import descriptor
  731.         auto pImportDesc = reinterpret_cast<PIMAGE_IMPORT_DESCRIPTOR>(
  732.             (BYTE*)lpFileContent +
  733.             pImportSection->PointerToRawData +
  734.             (importDir.VirtualAddress - pImportSection->VirtualAddress));
  735.  
  736.         // Process all DLLs
  737.         while (pImportDesc && pImportDesc->Name != 0) {
  738.             // Get DLL name
  739.             const char* dllName = reinterpret_cast<const char*>(
  740.                 (BYTE*)lpFileContent +
  741.                 pImportSection->PointerToRawData +
  742.                 (pImportDesc->Name - pImportSection->VirtualAddress));
  743.  
  744.             if (!IsBadReadPtr(dllName, 1)) {
  745.                 std::vector<wchar_t> wideDllName(MAX_PATH);
  746.                 MultiByteToWideChar(CP_ACP, 0, dllName, -1,
  747.                     wideDllName.data(), MAX_PATH);
  748.  
  749.                 // Print DLL information
  750.                 OUTPUT("\n\tDLL NAME : %s\r\n", wideDllName.data());
  751.                 OUTPUT("\tCharacteristics : 0x%X\r\n", pImportDesc->Characteristics);
  752.                 OUTPUT("\tOriginalFirstThunk : 0x%X\r\n", pImportDesc->OriginalFirstThunk);
  753.                 OUTPUT("\tTimeDateStamp : 0x%X\r\n", pImportDesc->TimeDateStamp);
  754.                 OUTPUT("\tForwarderChain : 0x%X\r\n", pImportDesc->ForwarderChain);
  755.                 OUTPUT("\tFirstThunk : 0x%X\r\n", pImportDesc->FirstThunk);
  756.  
  757.                 OUTPUT("\n\tImported Functions :\r\n\r\n");
  758.  
  759.                 // Process functions using OriginalFirstThunk
  760.                 if (pImportDesc->OriginalFirstThunk) {
  761.                     auto pThunk = reinterpret_cast<PIMAGE_THUNK_DATA>(
  762.                         (BYTE*)lpFileContent +
  763.                         pImportSection->PointerToRawData +
  764.                         (pImportDesc->OriginalFirstThunk - pImportSection->VirtualAddress));
  765.  
  766.                     // Process all functions for this DLL
  767.                     while (pThunk && pThunk->u1.AddressOfData) {
  768.                         if (!(pThunk->u1.Ordinal & IMAGE_ORDINAL_FLAG)) {
  769.                             auto pImportByName = reinterpret_cast<PIMAGE_IMPORT_BY_NAME>(
  770.                                 (BYTE*)lpFileContent +
  771.                                 pImportSection->PointerToRawData +
  772.                                 (pThunk->u1.AddressOfData - pImportSection->VirtualAddress));
  773.  
  774.                             if (!IsBadReadPtr(pImportByName, sizeof(IMAGE_IMPORT_BY_NAME))) {
  775.                                 std::vector<wchar_t> wideFuncName(MAX_PATH);
  776.                                 MultiByteToWideChar(CP_ACP, 0,
  777.                                     reinterpret_cast<const char*>(pImportByName->Name),
  778.                                     -1, wideFuncName.data(), MAX_PATH);
  779.  
  780.                                 OUTPUT("\t\t%s\r\n", wideFuncName.data());
  781.                             }
  782.                         }
  783.                         pThunk++;
  784.                     }
  785.                 }
  786.             }
  787.             pImportDesc++;
  788.         }
  789.     }
  790.  
  791.     ShowProgress(90);
  792.  
  793.     // In your AnalyzePEFile function, add this code after the imports section (before the cleanup label):
  794.  
  795.     // Handle Exports
  796.     const auto& exportDir = pImageNtHeaders->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT];
  797.     if (exportDir.VirtualAddress && exportDir.Size) {
  798.         OUTPUT("\n[+] EXPORTED FUNCTIONS\n");
  799.  
  800.         auto pSection = IMAGE_FIRST_SECTION(pImageNtHeaders);
  801.         PIMAGE_SECTION_HEADER pExportSection = PEHelpers::GetExportSection(
  802.             pSection,
  803.             pImageNtHeaders->FileHeader.NumberOfSections,
  804.             exportDir.VirtualAddress
  805.         );
  806.  
  807.         if (!pExportSection) {
  808.             OUTPUT("[-] Could not find export section\n");
  809.         }
  810.         else {
  811.             auto pExportDir = reinterpret_cast<PIMAGE_EXPORT_DIRECTORY>(
  812.                 (BYTE*)lpFileContent +
  813.                 pExportSection->PointerToRawData +
  814.                 (exportDir.VirtualAddress - pExportSection->VirtualAddress));
  815.  
  816.             const DWORD_PTR dRawOffset = reinterpret_cast<DWORD_PTR>(lpFileContent) +
  817.                 pExportSection->PointerToRawData;
  818.  
  819.             OUTPUT("\tNumber of Functions: %d\n", pExportDir->NumberOfFunctions);
  820.             OUTPUT("\tNumber of Names: %d\n", pExportDir->NumberOfNames);
  821.             OUTPUT("\tBase: %d\n", pExportDir->Base);
  822.  
  823.             // Fix for DLL name display
  824.             const char* dllName = reinterpret_cast<const char*>(
  825.                 (BYTE*)lpFileContent +
  826.                 pExportSection->PointerToRawData +
  827.                 (pExportDir->Name - pExportSection->VirtualAddress));
  828.  
  829.             std::vector<wchar_t> wideDllName(MAX_PATH);
  830.             MultiByteToWideChar(CP_ACP, 0, dllName, -1,
  831.                 wideDllName.data(), MAX_PATH);
  832.             OUTPUT("\tName: %s\n\n", wideDllName.data());
  833.  
  834.             const auto pArrayOfFunctionsNames = reinterpret_cast<DWORD*>(
  835.                 dRawOffset + (pExportDir->AddressOfNames - pExportSection->VirtualAddress));
  836.  
  837.             OUTPUT("\tExported Functions:\n\n");
  838.             for (DWORD i = 0; i < pExportDir->NumberOfNames; ++i) {
  839.                 const char* functionName = reinterpret_cast<const char*>(
  840.                     dRawOffset + (pArrayOfFunctionsNames[i] - pExportSection->VirtualAddress));
  841.  
  842.                 std::vector<wchar_t> wideFuncName(MAX_PATH);
  843.                 MultiByteToWideChar(CP_ACP, 0, functionName, -1,
  844.                     wideFuncName.data(), MAX_PATH);
  845.  
  846.                 OUTPUT("\t\t%s\n", wideFuncName.data());
  847.             }
  848.         }
  849.     }
  850.  
  851.     ShowProgress(100);
  852.  
  853.     SetStatusText(L"Analysis complete");
  854.  
  855. cleanup:
  856.     if (lpFileContent) {
  857.         UnmapViewOfFile(lpFileContent);
  858.     }
  859.     if (hFileMapping) {
  860.         CloseHandle(hFileMapping);
  861.     }
  862.     if (hFile) {
  863.         CloseHandle(hFile);
  864.     }
  865.  
  866.     UpdateEditControl();
  867. }
  868.  
  869. /*
  870. //use below vv ALWAYS
  871. void AnalyzePEFile(const wchar_t* filePathW) {
  872.     OUTPUT("[+] Starting PE Analysis for: %s\n\n", filePathW);
  873.  
  874.     LPVOID lpFileContent = GetFileContent(filePathW);
  875.     if (!lpFileContent) {
  876.         OUTPUT("[-] Failed to read file content!\n");
  877.         return;
  878.     }
  879.  
  880.     const auto pImageDosHeader = static_cast<PIMAGE_DOS_HEADER>(lpFileContent);
  881.     if (pImageDosHeader->e_magic != IMAGE_DOS_SIGNATURE) {
  882.         OUTPUT("[-] Invalid DOS signature!\n");
  883.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  884.         return;
  885.     }
  886.  
  887.     const auto pImageNtHeaders = reinterpret_cast<PIMAGE_NT_HEADERS>((DWORD_PTR)lpFileContent + pImageDosHeader->e_lfanew);
  888.     if (pImageNtHeaders->Signature != IMAGE_NT_SIGNATURE) {
  889.         OUTPUT("[-] Invalid NT signature!\n");
  890.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  891.         return;
  892.     }
  893.  
  894.     //UpdateEditControl(); //added just now remove line!
  895.  
  896.     OUTPUT("[+] PE FILE HEADER\n");
  897.     OUTPUT("\tMachine : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.Machine);
  898.     OUTPUT("\tNumberOfSections : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.NumberOfSections);
  899.     OUTPUT("\tTimeDateStamp : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.TimeDateStamp);
  900.     OUTPUT("\tPointerToSymbolTable : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.PointerToSymbolTable);
  901.     OUTPUT("\tNumberOfSymbols : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.NumberOfSymbols);
  902.     OUTPUT("\tSizeOfOptionalHeader : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.SizeOfOptionalHeader);
  903.     OUTPUT("\tCharacteristics : 0x%X %s\n\n", (uintptr_t)pImageNtHeaders->FileHeader.Characteristics, GetImageCharacteristics(pImageNtHeaders->FileHeader.Characteristics));
  904.  
  905.     OUTPUT("[+] PE OPTIONAL HEADER\n");
  906.     OUTPUT("\tMagic : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.Magic);
  907.     OUTPUT("\tAddressOfEntryPoint : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.AddressOfEntryPoint);
  908.     OUTPUT("\tImageBase : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.ImageBase);
  909.     OUTPUT("\tSectionAlignment : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SectionAlignment);
  910.     OUTPUT("\tFileAlignment : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.FileAlignment);
  911.     OUTPUT("\tMajorOperatingSystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorOperatingSystemVersion);
  912.     OUTPUT("\tMinorOperatingSystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorOperatingSystemVersion);
  913.     OUTPUT("\tMajorImageVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorImageVersion);
  914.     OUTPUT("\tMinorImageVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorImageVersion);
  915.     OUTPUT("\tMajorSubsystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorSubsystemVersion);
  916.     OUTPUT("\tMinorSubsystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorSubsystemVersion);
  917.     OUTPUT("\tWin32VersionValue : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.Win32VersionValue);
  918.     OUTPUT("\tSizeOfImage : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfImage);
  919.     OUTPUT("\tSizeOfHeaders : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeaders);
  920.     OUTPUT("\tCheckSum : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.CheckSum);
  921.     OUTPUT("\tSubsystem : 0x%X %s\n", (uintptr_t)pImageNtHeaders->OptionalHeader.Subsystem, GetSubsystem(pImageNtHeaders->OptionalHeader.Subsystem));
  922.     OUTPUT("\tDllCharacteristics : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.DllCharacteristics);
  923.     OUTPUT("\tSizeOfStackReserve : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfStackReserve);
  924.     OUTPUT("\tSizeOfStackCommit : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfStackCommit);
  925.     OUTPUT("\tSizeOfHeapReserve : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeapReserve);
  926.     OUTPUT("\tSizeOfHeapCommit : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeapCommit);
  927.     OUTPUT("\tLoaderFlags : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.LoaderFlags);
  928.     OUTPUT("\tNumberOfRvaAndSizes : 0x%X\n\n", (uintptr_t)pImageNtHeaders->OptionalHeader.NumberOfRvaAndSizes);
  929.  
  930.     //UpdateEditControl(); //added just now remove line!
  931.  
  932.     GetDataDirectories(&pImageNtHeaders->OptionalHeader.DataDirectory[0]);
  933.  
  934.     const auto pImageSectionHeader = reinterpret_cast<PIMAGE_SECTION_HEADER>((DWORD_PTR)pImageNtHeaders + sizeof(IMAGE_NT_HEADERS));
  935.     const auto pImageImportSection = GetSections(pImageSectionHeader, pImageNtHeaders->FileHeader.NumberOfSections, pImageNtHeaders->OptionalHeader.DataDirectory[1].VirtualAddress);
  936.  
  937.     if (!pImageImportSection) {
  938.         OUTPUT("[-] Error: Could not find import section!\n");
  939.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  940.         return;
  941.     }
  942.  
  943.     const auto pImageImportDescriptor = reinterpret_cast<PIMAGE_IMPORT_DESCRIPTOR>((DWORD_PTR)lpFileContent + pImageImportSection->PointerToRawData);
  944.     if (pImageNtHeaders->FileHeader.Machine == IMAGE_FILE_MACHINE_I386) {
  945.         GetImports32(pImageImportDescriptor, (DWORD)lpFileContent + pImageImportSection->PointerToRawData, pImageImportSection);
  946.     }
  947.     else if (pImageNtHeaders->FileHeader.Machine == IMAGE_FILE_MACHINE_AMD64) {
  948.         GetImports64(pImageImportDescriptor, (DWORD)lpFileContent + pImageImportSection->PointerToRawData, pImageImportSection);
  949.     }
  950.     else {
  951.         OUTPUT("[-] Unsupported architecture!\n");
  952.     }
  953.  
  954.     HeapFree(GetProcessHeap(), 0, lpFileContent);
  955.     UpdateEditControl();
  956. }
  957.  
  958. void GetDataDirectories(PIMAGE_DATA_DIRECTORY pImageDataDirectory) {
  959.     OUTPUT("[+] PE DATA DIRECTORIES\n");
  960.     for (int i = 0; i < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; ++i, ++pImageDataDirectory) {
  961.         if (pImageDataDirectory->VirtualAddress == 0) continue;
  962.         OUTPUT("\tDataDirectory (%s) VirtualAddress : 0x%X\n", GetDataDirectoryName(i), (uintptr_t)pImageDataDirectory->VirtualAddress);
  963.         OUTPUT("\tDataDirectory (%s) Size : 0x%X\n\n", GetDataDirectoryName(i), (uintptr_t)pImageDataDirectory->Size);
  964.     }
  965. }
  966.  
  967. PIMAGE_SECTION_HEADER GetSections(const PIMAGE_SECTION_HEADER pImageSectionHeader, int NumberOfSections, DWORD dImportAddress) {
  968.     PIMAGE_SECTION_HEADER pImageImportHeader = nullptr;
  969.     OUTPUT("\n[+] PE IMAGE SECTIONS\n");
  970.     for (int i = 0; i < NumberOfSections; ++i) {
  971.         const auto pCurrentSectionHeader = reinterpret_cast<PIMAGE_SECTION_HEADER>((DWORD_PTR)pImageSectionHeader + i * sizeof(IMAGE_SECTION_HEADER));
  972.         OUTPUT("\n\tSECTION : %s\n", (wchar_t*)pCurrentSectionHeader->Name);
  973.         OUTPUT("\t\tMisc (PhysicalAddress) : 0x%X\n", (uintptr_t)pCurrentSectionHeader->Misc.PhysicalAddress);
  974.         OUTPUT("\t\tMisc (VirtualSize) : 0x%X\n", (uintptr_t)pCurrentSectionHeader->Misc.VirtualSize);
  975.         OUTPUT("\t\tVirtualAddress : 0x%X\n", (uintptr_t)pCurrentSectionHeader->VirtualAddress);
  976.         OUTPUT("\t\tSizeOfRawData : 0x%X\n", (uintptr_t)pCurrentSectionHeader->SizeOfRawData);
  977.         OUTPUT("\t\tPointerToRawData : 0x%X\n", (uintptr_t)pCurrentSectionHeader->PointerToRawData);
  978.         OUTPUT("\t\tCharacteristics : 0x%X %s\n", (uintptr_t)pCurrentSectionHeader->Characteristics, GetSectionProtection(pCurrentSectionHeader->Characteristics));
  979.  
  980.         if (dImportAddress >= pCurrentSectionHeader->VirtualAddress && dImportAddress < pCurrentSectionHeader->VirtualAddress + pCurrentSectionHeader->Misc.VirtualSize) {
  981.             pImageImportHeader = pCurrentSectionHeader;
  982.         }
  983.     }
  984.     return pImageImportHeader;
  985. }
  986.  
  987. void GetImports32(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor, DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection) {
  988.     OUTPUT("\n[+] IMPORTED DLL\n");
  989.     while (pImageImportDescriptor->Name != 0) {
  990.         OUTPUT("\n\tDLL NAME : %s\n", (wchar_t*)(dRawOffset + (pImageImportDescriptor->Name - pImageImportSection->VirtualAddress)));
  991.         if (pImageImportDescriptor->OriginalFirstThunk == 0) {
  992.             ++pImageImportDescriptor;
  993.             continue;
  994.         }
  995.         auto pOriginalFirstThunk = reinterpret_cast<PIMAGE_THUNK_DATA32>(dRawOffset + (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress));
  996.         while (pOriginalFirstThunk->u1.AddressOfData != 0) {
  997.             const auto pImageImportByName = reinterpret_cast<PIMAGE_IMPORT_BY_NAME>(dRawOffset + (pOriginalFirstThunk->u1.AddressOfData - pImageImportSection->VirtualAddress));
  998.             if (pImageImportByName) {
  999.                 OUTPUT("\t\tFunction: %s\n", (char*)pImageImportByName->Name);
  1000.             }
  1001.             pOriginalFirstThunk++;
  1002.         }
  1003.         pImageImportDescriptor++;
  1004.     }
  1005. }
  1006.  
  1007. void GetImports64(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor, DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection) {
  1008.     OUTPUT("\n[+] IMPORTED DLL\n");
  1009.     while (pImageImportDescriptor->Name != 0) {
  1010.         OUTPUT("\n\tDLL NAME : %s\n", (wchar_t*)(dRawOffset + (pImageImportDescriptor->Name - pImageImportSection->VirtualAddress)));
  1011.         if (pImageImportDescriptor->OriginalFirstThunk == 0) {
  1012.             ++pImageImportDescriptor;
  1013.             continue;
  1014.         }
  1015.         auto pOriginalFirstThunk = reinterpret_cast<PIMAGE_THUNK_DATA64>(dRawOffset + (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress));
  1016.         while (pOriginalFirstThunk->u1.AddressOfData != 0) {
  1017.             const auto pImageImportByName = reinterpret_cast<PIMAGE_IMPORT_BY_NAME>(dRawOffset + (pOriginalFirstThunk->u1.AddressOfData - pImageImportSection->VirtualAddress));
  1018.             if (pImageImportByName) {
  1019.                 OUTPUT("\t\tFunction: %s\n", (char*)pImageImportByName->Name);
  1020.             }
  1021.             pOriginalFirstThunk++;
  1022.         }
  1023.         pImageImportDescriptor++;
  1024.     }
  1025. }
  1026. //use above ^^ ALWAYS
  1027. */
  1028.  
  1029.  
  1030. /*
  1031. // older-orig-deprecated vv
  1032. // Main PE Analysis function
  1033. void AnalyzePEFile(const wchar_t* filePathW)
  1034. {
  1035.     //WCHAR filePathW[MAX_PATH];
  1036.     //MultiByteToWideChar(CP_ACP, 0, filePathA, -1, filePathW, MAX_PATH);
  1037.     OUTPUT("[+] Starting PE Analysis for: %s\n\n", filePathW);
  1038.     //AppendToOutput(L"[+] Starting PE Analysis for: %ls\n\n", filePathW);
  1039.  
  1040.     // Get file content
  1041.     LPVOID lpFileContent = GetFileContent(filePathW);
  1042.     if (!lpFileContent)
  1043.     {
  1044.         OUTPUT("[-] Failed to read file content!\n");
  1045.         return;
  1046.     }
  1047.  
  1048.     // Get DOS header
  1049.     const auto pImageDosHeader = static_cast<PIMAGE_DOS_HEADER>(lpFileContent);
  1050.     if (pImageDosHeader->e_magic != IMAGE_DOS_SIGNATURE)
  1051.     {
  1052.         OUTPUT("[-] Invalid DOS signature!\n");
  1053.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  1054.         return;
  1055.     }
  1056.  
  1057.     // Get NT headers
  1058.     const auto pImageNtHeaders = reinterpret_cast<PIMAGE_NT_HEADERS>((DWORD_PTR)lpFileContent + pImageDosHeader->e_lfanew);
  1059.     if (pImageNtHeaders->Signature != IMAGE_NT_SIGNATURE)
  1060.     {
  1061.         OUTPUT("[-] Invalid NT signature!\n");
  1062.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  1063.         return;
  1064.     }
  1065.  
  1066.     // Display File Header information
  1067.     OUTPUT("[+] PE FILE HEADER\n");
  1068.     OUTPUT("\tMachine : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.Machine);
  1069.     OUTPUT("\tNumberOfSections : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.NumberOfSections);
  1070.     OUTPUT("\tTimeDateStamp : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.TimeDateStamp);
  1071.     OUTPUT("\tPointerToSymbolTable : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.PointerToSymbolTable);
  1072.     OUTPUT("\tNumberOfSymbols : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.NumberOfSymbols);
  1073.     OUTPUT("\tSizeOfOptionalHeader : 0x%X\n", (uintptr_t)pImageNtHeaders->FileHeader.SizeOfOptionalHeader);
  1074.     OUTPUT("\tCharacteristics : 0x%X %s\n\n",
  1075.         (uintptr_t)pImageNtHeaders->FileHeader.Characteristics,
  1076.         GetImageCharacteristics(pImageNtHeaders->FileHeader.Characteristics));
  1077.  
  1078.     // Display Optional Header information
  1079.     OUTPUT("[+] PE OPTIONAL HEADER\n");
  1080.     OUTPUT("\tMagic : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.Magic);
  1081.     OUTPUT("\tAddressOfEntryPoint : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.AddressOfEntryPoint);
  1082.     OUTPUT("\tImageBase : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.ImageBase);
  1083.     OUTPUT("\tSectionAlignment : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SectionAlignment);
  1084.     OUTPUT("\tFileAlignment : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.FileAlignment);
  1085.     OUTPUT("\tMajorOperatingSystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorOperatingSystemVersion);
  1086.     OUTPUT("\tMinorOperatingSystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorOperatingSystemVersion);
  1087.     OUTPUT("\tMajorImageVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorImageVersion);
  1088.     OUTPUT("\tMinorImageVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorImageVersion);
  1089.     OUTPUT("\tMajorSubsystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MajorSubsystemVersion);
  1090.     OUTPUT("\tMinorSubsystemVersion : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.MinorSubsystemVersion);
  1091.     OUTPUT("\tWin32VersionValue : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.Win32VersionValue);
  1092.     OUTPUT("\tSizeOfImage : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfImage);
  1093.     OUTPUT("\tSizeOfHeaders : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeaders);
  1094.     OUTPUT("\tCheckSum : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.CheckSum);
  1095.     OUTPUT("\tSubsystem : 0x%X %s\n",
  1096.         (uintptr_t)pImageNtHeaders->OptionalHeader.Subsystem,
  1097.         GetSubsystem(pImageNtHeaders->OptionalHeader.Subsystem));
  1098.     OUTPUT("\tDllCharacteristics : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.DllCharacteristics);
  1099.     OUTPUT("\tSizeOfStackReserve : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfStackReserve);
  1100.     OUTPUT("\tSizeOfStackCommit : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfStackCommit);
  1101.     OUTPUT("\tSizeOfHeapReserve : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeapReserve);
  1102.     OUTPUT("\tSizeOfHeapCommit : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.SizeOfHeapCommit);
  1103.     OUTPUT("\tLoaderFlags : 0x%X\n", (uintptr_t)pImageNtHeaders->OptionalHeader.LoaderFlags);
  1104.     OUTPUT("\tNumberOfRvaAndSizes : 0x%X\n\n", (uintptr_t)pImageNtHeaders->OptionalHeader.NumberOfRvaAndSizes);
  1105.  
  1106.     // Get Data Directories
  1107.     GetDataDirectories(&pImageNtHeaders->OptionalHeader.DataDirectory[0]);
  1108.  
  1109.     // Get the import section
  1110.     const auto pImageSectionHeader = reinterpret_cast<PIMAGE_SECTION_HEADER>(
  1111.         (DWORD_PTR)pImageNtHeaders + sizeof(IMAGE_NT_HEADERS));
  1112.  
  1113.     const auto pImageImportSection = GetSections(
  1114.         pImageSectionHeader,
  1115.         pImageNtHeaders->FileHeader.NumberOfSections,
  1116.         pImageNtHeaders->OptionalHeader.DataDirectory[1].VirtualAddress);
  1117.  
  1118.     if (!pImageImportSection)
  1119.     {
  1120.         OUTPUT("[-] Error: Could not find import section!\n");
  1121.         HeapFree(GetProcessHeap(), 0, lpFileContent);
  1122.         return;
  1123.     }
  1124.  
  1125.     // Get imports based on architecture
  1126.     const auto pImageImportDescriptor = reinterpret_cast<PIMAGE_IMPORT_DESCRIPTOR>(
  1127.         (DWORD_PTR)lpFileContent + pImageImportSection->PointerToRawData);
  1128.  
  1129.     if (pImageNtHeaders->FileHeader.Machine == IMAGE_FILE_MACHINE_I386)
  1130.     {
  1131.         GetImports32(
  1132.             pImageImportDescriptor,
  1133.             (DWORD)lpFileContent + pImageImportSection->PointerToRawData,
  1134.             pImageImportSection);
  1135.     }
  1136.     else if (pImageNtHeaders->FileHeader.Machine == IMAGE_FILE_MACHINE_AMD64)
  1137.     {
  1138.         GetImports64(
  1139.             pImageImportDescriptor,
  1140.             (DWORD)lpFileContent + pImageImportSection->PointerToRawData,
  1141.             pImageImportSection);
  1142.     }
  1143.     else
  1144.     {
  1145.         OUTPUT("[-] Unsupported architecture!\n");
  1146.     }
  1147.  
  1148.     // Cleanup
  1149.     HeapFree(GetProcessHeap(), 0, lpFileContent);
  1150.  
  1151.     // Update the GUI with the analysis results
  1152.     UpdateEditControl();
  1153. }
  1154.  
  1155. void GetDataDirectories(PIMAGE_DATA_DIRECTORY pImageDataDirectory)
  1156. {
  1157.     OUTPUT("[+] PE DATA DIRECTORIES\n");
  1158.     for (int i = 0; i < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; ++i, ++pImageDataDirectory)
  1159.     {
  1160.         if (pImageDataDirectory->VirtualAddress == 0)
  1161.             continue;
  1162.  
  1163.         OUTPUT("\tDataDirectory (%s) VirtualAddress : 0x%X\n",
  1164.             GetDataDirectoryName(i),
  1165.             (uintptr_t)pImageDataDirectory->VirtualAddress);
  1166.         OUTPUT("\tDataDirectory (%s) Size : 0x%X\n\n",
  1167.             GetDataDirectoryName(i),
  1168.             (uintptr_t)pImageDataDirectory->Size);
  1169.     }
  1170. }
  1171.  
  1172. PIMAGE_SECTION_HEADER GetSections(const PIMAGE_SECTION_HEADER pImageSectionHeader,
  1173.     int NumberOfSections, DWORD dImportAddress)
  1174. {
  1175.     PIMAGE_SECTION_HEADER pImageImportHeader = nullptr;
  1176.  
  1177.     OUTPUT("\n[+] PE IMAGE SECTIONS\n");
  1178.  
  1179.     for (int i = 0; i < NumberOfSections; ++i)
  1180.     {
  1181.         const auto pCurrentSectionHeader = (PIMAGE_SECTION_HEADER)((DWORD_PTR)pImageSectionHeader +
  1182.             i * sizeof(IMAGE_SECTION_HEADER));
  1183.  
  1184.         OUTPUT("\n\tSECTION : %s\n", (wchar_t*)pCurrentSectionHeader->Name);
  1185.         OUTPUT("\t\tMisc (PhysicalAddress) : 0x%X\n",
  1186.             (uintptr_t)pCurrentSectionHeader->Misc.PhysicalAddress);
  1187.         OUTPUT("\t\tMisc (VirtualSize) : 0x%X\n",
  1188.             (uintptr_t)pCurrentSectionHeader->Misc.VirtualSize);
  1189.         OUTPUT("\t\tVirtualAddress : 0x%X\n",
  1190.             (uintptr_t)pCurrentSectionHeader->VirtualAddress);
  1191.         OUTPUT("\t\tSizeOfRawData : 0x%X\n",
  1192.             (uintptr_t)pCurrentSectionHeader->SizeOfRawData);
  1193.         OUTPUT("\t\tPointerToRawData : 0x%X\n",
  1194.             (uintptr_t)pCurrentSectionHeader->PointerToRawData);
  1195.         OUTPUT("\t\tPointerToRelocations : 0x%X\n",
  1196.             (uintptr_t)pCurrentSectionHeader->PointerToRelocations);
  1197.         OUTPUT("\t\tPointerToLinenumbers : 0x%X\n",
  1198.             (uintptr_t)pCurrentSectionHeader->PointerToLinenumbers);
  1199.         OUTPUT("\t\tNumberOfRelocations : 0x%X\n",
  1200.             (uintptr_t)pCurrentSectionHeader->NumberOfRelocations);
  1201.         OUTPUT("\t\tNumberOfLinenumbers : 0x%X\n",
  1202.             (uintptr_t)pCurrentSectionHeader->NumberOfLinenumbers);
  1203.         OUTPUT("\t\tCharacteristics : 0x%X %s\n",
  1204.             (uintptr_t)pCurrentSectionHeader->Characteristics,
  1205.             GetSectionProtection(pCurrentSectionHeader->Characteristics));
  1206.  
  1207.         if (dImportAddress >= pCurrentSectionHeader->VirtualAddress &&
  1208.             dImportAddress < pCurrentSectionHeader->VirtualAddress +
  1209.             pCurrentSectionHeader->Misc.VirtualSize)
  1210.         {
  1211.             pImageImportHeader = pCurrentSectionHeader;
  1212.         }
  1213.     }
  1214.  
  1215.     return pImageImportHeader;
  1216. }
  1217. void GetImports32(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor,
  1218.     DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection)
  1219. {
  1220.     OUTPUT("\n[+] IMPORTED DLL\n");
  1221.  
  1222.     while (pImageImportDescriptor->Name != 0)
  1223.     {
  1224.         OUTPUT("\n\tDLL NAME : %s\n",
  1225.             (wchar_t*)(dRawOffset + (pImageImportDescriptor->Name - pImageImportSection->VirtualAddress)));
  1226.         OUTPUT("\tCharacteristics : 0x%X\n",
  1227.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->Characteristics - pImageImportSection->VirtualAddress)));
  1228.         OUTPUT("\tOriginalFirstThunk : 0x%X\n",
  1229.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress)));
  1230.         OUTPUT("\tTimeDateStamp : 0x%X\n",
  1231.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->TimeDateStamp - pImageImportSection->VirtualAddress)));
  1232.         OUTPUT("\tForwarderChain : 0x%X\n",
  1233.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->ForwarderChain - pImageImportSection->VirtualAddress)));
  1234.         OUTPUT("\tFirstThunk : 0x%X\n",
  1235.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->FirstThunk - pImageImportSection->VirtualAddress)));
  1236.  
  1237.         if (pImageImportDescriptor->OriginalFirstThunk == 0)
  1238.         {
  1239.             ++pImageImportDescriptor;
  1240.             continue;
  1241.         }
  1242.  
  1243.         auto pOriginalFirstThrunk = (PIMAGE_THUNK_DATA32)(dRawOffset +
  1244.             (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress));
  1245.  
  1246.         OUTPUT("\n\tImported Functions : \n\n");
  1247.  
  1248.         while (pOriginalFirstThrunk->u1.AddressOfData != 0)
  1249.         {
  1250.             if (pOriginalFirstThrunk->u1.AddressOfData >= IMAGE_ORDINAL_FLAG32)
  1251.             {
  1252.                 ++pOriginalFirstThrunk;
  1253.                 continue;
  1254.             }
  1255.  
  1256.             const auto pImageImportByName = (PIMAGE_IMPORT_BY_NAME)(dRawOffset +
  1257.                 (pOriginalFirstThrunk->u1.AddressOfData - pImageImportSection->VirtualAddress));
  1258.  
  1259.             if (pImageImportByName == nullptr)
  1260.             {
  1261.                 ++pOriginalFirstThrunk;
  1262.                 continue;
  1263.             }
  1264.  
  1265.             if (pOriginalFirstThrunk->u1.Ordinal & IMAGE_ORDINAL_FLAG32)
  1266.             {
  1267.                 OUTPUT("\t\t0x%X (Ordinal) : %s\n",
  1268.                     (uintptr_t)pOriginalFirstThrunk->u1.AddressOfData,
  1269.                     (wchar_t*)((DWORD_PTR)dRawOffset + (pImageImportByName->Name - pImageImportSection->VirtualAddress)));
  1270.             }
  1271.             else
  1272.             {
  1273.                 OUTPUT("\t\t%s\n",
  1274.                     (wchar_t*)((DWORD_PTR)dRawOffset + (pImageImportByName->Name - pImageImportSection->VirtualAddress)));
  1275.             }
  1276.  
  1277.             ++pOriginalFirstThrunk;
  1278.         }
  1279.  
  1280.         ++pImageImportDescriptor;
  1281.     }
  1282. }
  1283.  
  1284. void GetImports64(PIMAGE_IMPORT_DESCRIPTOR pImageImportDescriptor,
  1285.     DWORD dRawOffset, const PIMAGE_SECTION_HEADER pImageImportSection)
  1286. {
  1287.     OUTPUT("\n[+] IMPORTED DLL\n");
  1288.  
  1289.     while (pImageImportDescriptor->Name != 0)
  1290.     {
  1291.         OUTPUT("\n\tDLL NAME : %s\n",
  1292.             (wchar_t*)(dRawOffset + (pImageImportDescriptor->Name - pImageImportSection->VirtualAddress)));
  1293.         OUTPUT("\tCharacteristics : 0x%X\n",
  1294.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->Characteristics - pImageImportSection->VirtualAddress)));
  1295.         OUTPUT("\tOriginalFirstThunk : 0x%X\n",
  1296.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress)));
  1297.         OUTPUT("\tTimeDateStamp : 0x%X\n",
  1298.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->TimeDateStamp - pImageImportSection->VirtualAddress)));
  1299.         OUTPUT("\tForwarderChain : 0x%X\n",
  1300.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->ForwarderChain - pImageImportSection->VirtualAddress)));
  1301.         OUTPUT("\tFirstThunk : 0x%X\n",
  1302.             (uintptr_t)(dRawOffset + (pImageImportDescriptor->FirstThunk - pImageImportSection->VirtualAddress)));
  1303.  
  1304.         if (pImageImportDescriptor->OriginalFirstThunk == 0)
  1305.         {
  1306.             ++pImageImportDescriptor;
  1307.             continue;
  1308.         }
  1309.  
  1310.         auto pOriginalFirstThrunk = (PIMAGE_THUNK_DATA64)(dRawOffset +
  1311.             (pImageImportDescriptor->OriginalFirstThunk - pImageImportSection->VirtualAddress));
  1312.  
  1313.         OUTPUT("\n\tImported Functions : \n\n");
  1314.  
  1315.         while (pOriginalFirstThrunk->u1.AddressOfData != 0)
  1316.         {
  1317.             if (pOriginalFirstThrunk->u1.AddressOfData >= IMAGE_ORDINAL_FLAG64)
  1318.             {
  1319.                 ++pOriginalFirstThrunk;
  1320.                 continue;
  1321.             }
  1322.  
  1323.             const auto pImageImportByName = (PIMAGE_IMPORT_BY_NAME)((DWORD_PTR)dRawOffset +
  1324.                 (pOriginalFirstThrunk->u1.AddressOfData - pImageImportSection->VirtualAddress));
  1325.  
  1326.             if (pImageImportByName == nullptr)
  1327.             {
  1328.                 ++pOriginalFirstThrunk;
  1329.                 continue;
  1330.             }
  1331.  
  1332.             if (pOriginalFirstThrunk->u1.Ordinal & IMAGE_ORDINAL_FLAG64)
  1333.             {
  1334.                 OUTPUT("\t\t0x%llX (Ordinal) : %s\n",
  1335.                     pOriginalFirstThrunk->u1.AddressOfData,
  1336.                     (wchar_t*)((DWORD_PTR)dRawOffset + (pImageImportByName->Name - pImageImportSection->VirtualAddress)));
  1337.             }
  1338.             else
  1339.             {
  1340.                 OUTPUT("\t\t%s\n",
  1341.                     (wchar_t*)((DWORD_PTR)dRawOffset + (pImageImportByName->Name - pImageImportSection->VirtualAddress)));
  1342.             }
  1343.  
  1344.             ++pOriginalFirstThrunk;
  1345.         }
  1346.  
  1347.         ++pImageImportDescriptor;
  1348.     }
  1349. }
  1350. // older-orig-deprecated ^^
  1351. */
  1352.  
  1353. //filePathW
  1354. //lpFilePath
  1355. HANDLE GetFileContent(const wchar_t* lpFilePath) {
  1356.     HANDLE hFile = CreateFileW(lpFilePath, GENERIC_READ, 0, nullptr, OPEN_EXISTING, 0, nullptr);
  1357.     if (hFile == INVALID_HANDLE_VALUE) return nullptr;
  1358.     DWORD fileSize = GetFileSize(hFile, nullptr);
  1359.     auto lpFileContent = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, fileSize);
  1360.     DWORD bytesRead;
  1361.     ReadFile(hFile, lpFileContent, fileSize, &bytesRead, nullptr);
  1362.     CloseHandle(hFile);
  1363.     return lpFileContent;
  1364. }
  1365.  
  1366. void UpdateEditControl() {
  1367.     SetWindowTextW(g_hEditControl, g_OutputText.str().c_str());
  1368.     SendMessage(g_hEditControl, EM_SETSEL, -1, -1);
  1369.     SendMessage(g_hEditControl, EM_SCROLLCARET, 0, 0);
  1370. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement