Aktualizacja: 2025-10-16 11:10:36
This commit is contained in:
@@ -1,10 +1,5 @@
|
||||
/**
|
||||
* @file Controller.h
|
||||
* @brief Main orchestration class for KVC Framework operations
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*/
|
||||
// Controller.h
|
||||
// Main orchestration class for KVC Framework operations
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -80,10 +75,8 @@ struct RegistryMasterKey
|
||||
bool isDecrypted = false;
|
||||
};
|
||||
|
||||
/**
|
||||
* Main controller class managing kernel driver, process protection,
|
||||
* memory dumping, DPAPI extraction, and system operations
|
||||
*/
|
||||
// Main controller class managing kernel driver, process protection,
|
||||
// memory dumping, DPAPI extraction, and system operations
|
||||
class Controller
|
||||
{
|
||||
public:
|
||||
@@ -101,7 +94,7 @@ public:
|
||||
ULONG_PTR GetCiOptionsAddress() const noexcept;
|
||||
bool GetDSEStatus(ULONG_PTR& outAddress, DWORD& outValue) noexcept;
|
||||
|
||||
// Handles removal and restoration of system watermark related to signature hijacking.
|
||||
// Handles removal and restoration of system watermark related to signature hijacking
|
||||
bool RemoveWatermark() noexcept;
|
||||
bool RestoreWatermark() noexcept;
|
||||
std::wstring GetWatermarkStatus() noexcept;
|
||||
|
||||
@@ -1,14 +1,5 @@
|
||||
/**
|
||||
* @file DefenderManager.h
|
||||
* @brief Windows Defender Security Engine manipulation through registry-level operations
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Provides registry-level manipulation of Windows Defender service dependencies
|
||||
* to enable/disable the security engine, bypassing tamper protection mechanisms.
|
||||
* Requires administrator privileges and system restart for changes to take effect.
|
||||
*/
|
||||
// DefenderManager.h
|
||||
// Windows Defender security engine control via registry operations (privileged, restart required)
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -17,245 +8,68 @@
|
||||
#include <vector>
|
||||
#include <memory>
|
||||
|
||||
/**
|
||||
* @class DefenderManager
|
||||
* @brief Windows Defender Security Engine management through registry manipulation
|
||||
*
|
||||
* This class provides low-level control over Windows Defender by modifying
|
||||
* service dependencies in the registry. Works by changing RPC service dependencies
|
||||
* (RpcSs <-> RpcSt) to enable or disable the security engine.
|
||||
*
|
||||
* Features:
|
||||
* - Registry-level Defender engine control
|
||||
* - Bypasses Windows Defender tamper protection
|
||||
* - Atomic operations with rollback on failure
|
||||
* - Service dependency manipulation
|
||||
* - Privilege escalation for registry access
|
||||
*
|
||||
* @warning Requires SE_BACKUP_NAME, SE_RESTORE_NAME, and SE_LOAD_DRIVER_NAME privileges
|
||||
* @warning System restart required for changes to take effect
|
||||
* @warning Bypasses Windows Defender tamper protection
|
||||
*/
|
||||
// Manage Windows Defender by swapping service dependencies in the registry (requires privileges, restart)
|
||||
class DefenderManager {
|
||||
public:
|
||||
/**
|
||||
* @brief Security engine state enumeration
|
||||
*
|
||||
* Represents current state of Windows Defender security engine
|
||||
* based on service dependency configuration.
|
||||
*/
|
||||
// Security engine state based on WinDefend service dependency
|
||||
enum class SecurityState {
|
||||
ENABLED, ///< Windows Defender security engine is active (RpcSs dependency)
|
||||
DISABLED, ///< Windows Defender security engine is inactive (RpcSt dependency)
|
||||
UNKNOWN ///< Unable to determine security engine state
|
||||
ENABLED, // Defender engine active (RpcSs)
|
||||
DISABLED, // Defender engine inactive (RpcSt)
|
||||
UNKNOWN // State could not be determined
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Disables Windows Defender security engine
|
||||
*
|
||||
* Modifies Windows Defender service dependencies to prevent engine startup.
|
||||
* Changes RpcSs (active) dependency to RpcSt (inactive stub service).
|
||||
*
|
||||
* Operation:
|
||||
* 1. Enables required privileges
|
||||
* 2. Creates registry snapshot
|
||||
* 3. Modifies WinDefend service dependencies
|
||||
* 4. Restores modified registry
|
||||
*
|
||||
* @return bool true if operation successful, false on failure
|
||||
*
|
||||
* @note Requires administrator privileges
|
||||
* @note System restart required for changes to take effect
|
||||
* @warning This bypasses Windows Defender tamper protection
|
||||
*/
|
||||
// Disable Windows Defender by changing service dependency to RpcSt (requires admin + restart)
|
||||
static bool DisableSecurityEngine() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Enables Windows Defender security engine
|
||||
*
|
||||
* Restores Windows Defender service dependencies to normal operation.
|
||||
* Changes RpcSt (inactive) dependency back to RpcSs (active service).
|
||||
*
|
||||
* Operation:
|
||||
* 1. Enables required privileges
|
||||
* 2. Creates registry snapshot
|
||||
* 3. Restores original dependencies
|
||||
* 4. Restores modified registry
|
||||
*
|
||||
* @return bool true if operation successful, false on failure
|
||||
*
|
||||
* @note Requires administrator privileges
|
||||
* @note System restart required for changes to take effect
|
||||
*/
|
||||
// Enable Windows Defender by restoring service dependency to RpcSs (requires admin + restart)
|
||||
static bool EnableSecurityEngine() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Queries current Windows Defender security engine state
|
||||
*
|
||||
* Reads Windows Defender service dependencies from registry to determine
|
||||
* if the security engine is enabled (RpcSs), disabled (RpcSt), or unknown.
|
||||
*
|
||||
* @return SecurityState Current state of Windows Defender security engine
|
||||
*
|
||||
* @note Does not require elevated privileges for read-only query
|
||||
* @note Safe operation - no system modifications
|
||||
*/
|
||||
// Query current Defender state by reading service dependency (read-only, safe)
|
||||
static SecurityState GetSecurityEngineStatus() noexcept;
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief Registry snapshot context for atomic operations
|
||||
*
|
||||
* Holds temporary registry hive files and paths for atomic
|
||||
* modification of Windows Defender service configuration.
|
||||
* Provides automatic cleanup via destructor.
|
||||
*/
|
||||
// Temporary registry snapshot context for atomic service-hive modifications
|
||||
struct RegistryContext {
|
||||
std::wstring tempPath; ///< Temporary working directory path
|
||||
std::wstring hiveFile; ///< Saved registry hive file path
|
||||
std::wstring tempPath; // Temp directory for hive files
|
||||
std::wstring hiveFile; // Saved Services hive path
|
||||
|
||||
/**
|
||||
* @brief Default constructor
|
||||
*/
|
||||
RegistryContext() = default;
|
||||
~RegistryContext() { Cleanup(); } // Auto-cleanup of temp files
|
||||
|
||||
/**
|
||||
* @brief Destructor - automatically cleans up temporary files
|
||||
*
|
||||
* Ensures all temporary files are removed when context
|
||||
* goes out of scope, even in case of exceptions.
|
||||
*/
|
||||
~RegistryContext() { Cleanup(); }
|
||||
RegistryContext(const RegistryContext&) = delete;
|
||||
RegistryContext& operator=(const RegistryContext&) = delete;
|
||||
RegistryContext(RegistryContext&&) = default;
|
||||
RegistryContext& operator=(RegistryContext&&) = default;
|
||||
|
||||
// Non-copyable, movable
|
||||
RegistryContext(const RegistryContext&) = delete; ///< Copy constructor deleted
|
||||
RegistryContext& operator=(const RegistryContext&) = delete; ///< Copy assignment deleted
|
||||
RegistryContext(RegistryContext&&) = default; ///< Move constructor
|
||||
RegistryContext& operator=(RegistryContext&&) = default; ///< Move assignment
|
||||
|
||||
/**
|
||||
* @brief Cleans up temporary registry files and transaction logs
|
||||
*
|
||||
* Removes all temporary files created during registry operations:
|
||||
* - Main hive file (.hiv)
|
||||
* - Transaction logs (.LOG1, .LOG2)
|
||||
* - Binary log files (.blf)
|
||||
* - Registry transaction files (.regtrans-ms)
|
||||
*
|
||||
* @note Safe to call multiple times (idempotent operation)
|
||||
* @note Handles file locking and access violations
|
||||
*/
|
||||
// Remove temporary hive and transaction files (idempotent, handles locks)
|
||||
void Cleanup() noexcept;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Core registry manipulation logic for enable/disable operations
|
||||
*
|
||||
* Workflow:
|
||||
* 1. Enables required privileges (SE_BACKUP_NAME, SE_RESTORE_NAME, SE_LOAD_DRIVER_NAME)
|
||||
* 2. Creates registry snapshot of Services hive
|
||||
* 3. Modifies Windows Defender service dependencies
|
||||
* 4. Restores modified registry snapshot to live registry
|
||||
*
|
||||
* @param enable true to enable Defender, false to disable
|
||||
* @return bool true if all operations successful, false on any failure
|
||||
*
|
||||
* @note Atomic operation - changes are rolled back on failure
|
||||
* @note Uses registry transaction pattern for safety
|
||||
*/
|
||||
// Core modify workflow (enable==true to enable engine, false to disable) using snapshot/restore
|
||||
static bool ModifySecurityEngine(bool enable) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Enables all required privileges for registry operations
|
||||
*
|
||||
* Required privileges:
|
||||
* - SE_BACKUP_NAME: Read registry hives
|
||||
* - SE_RESTORE_NAME: Write registry hives
|
||||
* - SE_LOAD_DRIVER_NAME: Load/unload registry hives
|
||||
*
|
||||
* @return bool true if all privileges enabled, false on any failure
|
||||
*
|
||||
* @note Essential for registry backup/restore operations
|
||||
*/
|
||||
// Enable required privileges: SE_BACKUP_NAME, SE_RESTORE_NAME, SE_LOAD_DRIVER_NAME
|
||||
static bool EnableRequiredPrivileges() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Creates temporary registry snapshot for atomic modifications
|
||||
*
|
||||
* Process:
|
||||
* 1. Determines system temp path (Windows\temp)
|
||||
* 2. Validates write access to temp directory
|
||||
* 3. Saves Services registry hive to temporary file
|
||||
* 4. Loads saved hive as HKLM\Temp for modification
|
||||
*
|
||||
* @param ctx [out] Registry context with temp paths and hive file location
|
||||
* @return bool true if snapshot created successfully, false on failure
|
||||
*
|
||||
* @note Creates Services.hiv file in Windows\temp directory
|
||||
* @note Isolated environment for safe registry manipulation
|
||||
*/
|
||||
// Create temporary Services hive snapshot and load it under HKLM\Temp
|
||||
static bool CreateRegistrySnapshot(RegistryContext& ctx) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Modifies Windows Defender service dependencies in temp registry
|
||||
*
|
||||
* Changes RPC service dependency in WinDefend service:
|
||||
* - Enable: RpcSt (inactive) → RpcSs (active)
|
||||
* - Disable: RpcSs (active) → RpcSt (inactive)
|
||||
*
|
||||
* @param ctx Registry context with loaded temp hive
|
||||
* @param enable true to enable Defender, false to disable
|
||||
* @return bool true if dependency modification successful, false on failure
|
||||
*
|
||||
* @note Operates on HKLM\Temp\WinDefend key, not live registry
|
||||
* @note Uses REG_MULTI_SZ value type for service dependencies
|
||||
*/
|
||||
// Switch WinDefend DependOnService between RpcSt and RpcSs inside temp hive
|
||||
static bool ModifyDefenderDependencies(const RegistryContext& ctx, bool enable) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Restores modified registry snapshot to live system registry
|
||||
*
|
||||
* Process:
|
||||
* 1. Unloads temporary HKLM\Temp registry hive
|
||||
* 2. Restores modified hive to HKLM\SYSTEM\CurrentControlSet\Services
|
||||
* 3. Commits changes to live registry
|
||||
*
|
||||
* @param ctx Registry context with modified hive file
|
||||
* @return bool true if restore successful, false on failure
|
||||
*
|
||||
* @warning This operation modifies the live system registry
|
||||
* @note Uses REG_FORCE_RESTORE to overwrite existing registry data
|
||||
* @note Critical operation - affects system security configuration
|
||||
*/
|
||||
// Unload temp hive and restore modified snapshot to live Services key (critical operation)
|
||||
static bool RestoreRegistrySnapshot(const RegistryContext& ctx) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Reads REG_MULTI_SZ registry value as string vector
|
||||
* @param key Open registry key handle
|
||||
* @param valueName Name of REG_MULTI_SZ value to read
|
||||
* @return std::vector<std::wstring> Vector of strings or empty on failure
|
||||
*
|
||||
* @note Returns empty vector if value doesn't exist or wrong type
|
||||
* @note Handles double null-terminated string format
|
||||
*/
|
||||
// Read REG_MULTI_SZ into vector; returns empty vector on error or missing value
|
||||
static std::vector<std::wstring> ReadMultiString(HKEY key, const std::wstring& valueName) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Writes string vector to REG_MULTI_SZ registry value
|
||||
* @param key Open registry key handle
|
||||
* @param valueName Name of REG_MULTI_SZ value to write
|
||||
* @param values Vector of strings to write
|
||||
* @return bool true if write successful, false on failure
|
||||
*
|
||||
* @note Properly formats with double null terminator
|
||||
* @note Handles empty vectors and single string cases
|
||||
*/
|
||||
// Write vector as REG_MULTI_SZ (handles empty/single entries and double-null terminator)
|
||||
static bool WriteMultiString(HKEY key, const std::wstring& valueName, const std::vector<std::wstring>& values) noexcept;
|
||||
|
||||
// Registry constants
|
||||
static constexpr const wchar_t* WINDEFEND_KEY = L"SYSTEM\\CurrentControlSet\\Services\\WinDefend"; ///< Windows Defender service registry key
|
||||
static constexpr const wchar_t* SERVICES_KEY = L"SYSTEM\\CurrentControlSet\\Services"; ///< Windows Services root registry key
|
||||
static constexpr const wchar_t* DEPEND_VALUE = L"DependOnService"; ///< Service dependency value name
|
||||
static constexpr const wchar_t* RPC_SERVICE_ACTIVE = L"RpcSs"; ///< Active RPC service (enables Defender)
|
||||
static constexpr const wchar_t* RPC_SERVICE_INACTIVE = L"RpcSt"; ///< Inactive RPC stub (disables Defender)
|
||||
};
|
||||
static constexpr const wchar_t* WINDEFEND_KEY = L"SYSTEM\\CurrentControlSet\\Services\\WinDefend";
|
||||
static constexpr const wchar_t* SERVICES_KEY = L"SYSTEM\\CurrentControlSet\\Services";
|
||||
static constexpr const wchar_t* DEPEND_VALUE = L"DependOnService";
|
||||
static constexpr const wchar_t* RPC_SERVICE_ACTIVE = L"RpcSs";
|
||||
static constexpr const wchar_t* RPC_SERVICE_INACTIVE = L"RpcSt";
|
||||
};
|
||||
|
||||
@@ -1,14 +1,5 @@
|
||||
/**
|
||||
* @file HiveManager.h
|
||||
* @brief Registry hive backup, restore and defragmentation manager
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Provides atomic registry operations with TrustedInstaller privileges,
|
||||
* supporting full system registry backup and point-in-time restoration.
|
||||
* Handles locked system hives and provides defragmentation capabilities.
|
||||
*/
|
||||
// HiveManager.h
|
||||
// Registry hive backup, restore and defragmentation manager (TrustedInstaller, destructive ops)
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -19,338 +10,102 @@
|
||||
|
||||
namespace fs = std::filesystem;
|
||||
|
||||
// Forward declaration
|
||||
// Forward declaration of TrustedInstallerIntegrator class
|
||||
class TrustedInstallerIntegrator;
|
||||
|
||||
/**
|
||||
* @class HiveManager
|
||||
* @brief Registry hive backup, restore and defragmentation manager
|
||||
*
|
||||
* Features:
|
||||
* - Full registry backup with TrustedInstaller access
|
||||
* - Atomic hive restoration with automatic reboot
|
||||
* - Registry defragmentation via export/import cycle
|
||||
* - Handles locked system hives (SAM, SECURITY, SYSTEM)
|
||||
* - Automatic temp file cleanup
|
||||
* - Statistics tracking for operations
|
||||
*
|
||||
* Supported Hives:
|
||||
* - SYSTEM, SOFTWARE, SAM, SECURITY
|
||||
* - DEFAULT, NTUSER.DAT, UsrClass.dat
|
||||
* - User-specific hives with SID resolution
|
||||
*
|
||||
* @note Requires TrustedInstaller privileges for full functionality
|
||||
* @warning Registry operations can affect system stability
|
||||
*/
|
||||
// Manage registry hives: backup, restore and defragment (supports system and user hives; TI required)
|
||||
class HiveManager
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* @brief Construct hive manager and initialize TrustedInstaller
|
||||
*
|
||||
* Initializes internal state, acquires TrustedInstaller token,
|
||||
* and gathers current user information (SID, username).
|
||||
*
|
||||
* @note Automatically gets current user SID and username
|
||||
*/
|
||||
// Acquire TrustedInstaller, gather user info and initialize internal state
|
||||
HiveManager();
|
||||
|
||||
/**
|
||||
* @brief Destructor with token cleanup
|
||||
*
|
||||
* Releases TrustedInstaller token and reverts any active
|
||||
* impersonation. Ensures clean state on destruction.
|
||||
*/
|
||||
// Release TrustedInstaller token and clean up on destruction
|
||||
~HiveManager();
|
||||
|
||||
// === Main Operations ===
|
||||
|
||||
/**
|
||||
* @brief Backup all registry hives to directory
|
||||
* @param targetPath Backup directory (empty = auto-generate)
|
||||
* @return true if backup successful
|
||||
*
|
||||
* Performs complete registry backup including:
|
||||
* - System hives (SYSTEM, SOFTWARE, SAM, SECURITY)
|
||||
* - User hives (DEFAULT, NTUSER.DAT, UsrClass.dat)
|
||||
* - Registry statistics collection
|
||||
* - Automatic directory creation
|
||||
*
|
||||
* Auto-generates path format: C:\RegistryBackup_{User}_{Timestamp}
|
||||
*
|
||||
* @note Requires TrustedInstaller privileges
|
||||
* @note Uses RegSaveKeyW for atomic hive saving
|
||||
*/
|
||||
// Backup all supported registry hives to target directory (TrustedInstaller required)
|
||||
bool Backup(const std::wstring& targetPath = L"");
|
||||
|
||||
/**
|
||||
* @brief Restore registry hives from backup directory
|
||||
* @param sourcePath Backup directory path
|
||||
* @return true if restoration successful
|
||||
*
|
||||
* Validates and restores registry hives from backup:
|
||||
* - Verifies backup file integrity
|
||||
* - Prompts for user confirmation
|
||||
* - Initiates system reboot for changes
|
||||
* - Uses RegRestoreKeyW for atomic restoration
|
||||
*
|
||||
* @note Validates backup files before restoration
|
||||
* @note Prompts for confirmation before reboot
|
||||
* @note System restart required for changes to take effect
|
||||
*/
|
||||
// Restore registry hives from backup directory and schedule reboot (validates files, destructive)
|
||||
bool Restore(const std::wstring& sourcePath);
|
||||
|
||||
/**
|
||||
* @brief Defragment registry hives
|
||||
* @param tempPath Temporary directory (empty = auto-generate)
|
||||
* @return true if defragmentation successful
|
||||
*
|
||||
* Performs registry defragmentation by:
|
||||
* - Exporting hives to temporary files
|
||||
* - Re-importing hives to compact storage
|
||||
* - Reducing registry file fragmentation
|
||||
* - Improving registry performance
|
||||
*
|
||||
* @note Exports hives to temp, then re-imports
|
||||
* @note Reduces registry file size and improves performance
|
||||
*/
|
||||
// Defragment registry hives via export/import cycle to reduce fragmentation
|
||||
bool Defrag(const std::wstring& tempPath = L"");
|
||||
|
||||
/**
|
||||
* @struct BackupStats
|
||||
* @brief Statistics for backup/restore operations
|
||||
*
|
||||
* Tracks operation metrics for reporting and validation.
|
||||
*/
|
||||
// Operation statistics for backup/restore runs
|
||||
struct BackupStats {
|
||||
size_t totalHives = 0; ///< Number of hives processed
|
||||
size_t successfulHives = 0; ///< Successfully backed up/restored hives
|
||||
size_t failedHives = 0; ///< Failed hive operations
|
||||
uint64_t totalBytes = 0; ///< Total bytes processed across all hives
|
||||
size_t totalHives = 0; // Hives processed
|
||||
size_t successfulHives = 0; // Successful operations
|
||||
size_t failedHives = 0; // Failed operations
|
||||
uint64_t totalBytes = 0; // Total bytes processed
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Get statistics from last operation
|
||||
* @return const BackupStats& Reference to backup statistics
|
||||
*
|
||||
* Provides access to operation statistics for display
|
||||
* and logging purposes.
|
||||
*
|
||||
* @note Statistics are reset at the start of each operation
|
||||
*/
|
||||
// Return stats from last operation (reset at start of each op)
|
||||
const BackupStats& GetLastStats() const { return m_lastStats; }
|
||||
|
||||
private:
|
||||
/**
|
||||
* @struct RegistryHive
|
||||
* @brief Registry hive definition and metadata
|
||||
*
|
||||
* Contains hive identification and operational information
|
||||
* for registry hive processing.
|
||||
*/
|
||||
// Registry hive metadata for processing
|
||||
struct RegistryHive {
|
||||
std::wstring name; ///< Hive name (e.g., "SYSTEM")
|
||||
std::wstring registryPath; ///< Registry path (e.g., "HKLM\\SYSTEM")
|
||||
bool canRestore; ///< Can be restored with RegRestoreKeyW
|
||||
std::wstring name; // Hive name (e.g., "SYSTEM")
|
||||
std::wstring registryPath; // Registry path (e.g., "HKLM\\SYSTEM")
|
||||
bool canRestore; // Restorable with RegRestoreKeyW
|
||||
};
|
||||
|
||||
// === Internal Operations ===
|
||||
|
||||
/**
|
||||
* @brief Backup all registry hives to target directory
|
||||
* @param targetDir Destination directory for backup files
|
||||
* @return true if all hives backed up successfully
|
||||
*
|
||||
* Iterates through all defined registry hives and saves
|
||||
* each to individual .hiv files in target directory.
|
||||
*
|
||||
* @note Uses SaveRegistryHive for individual hive operations
|
||||
*/
|
||||
// Save all configured registry hives to target directory (calls SaveRegistryHive)
|
||||
bool BackupRegistryHives(const fs::path& targetDir);
|
||||
|
||||
/**
|
||||
* @brief Restore registry hives from backup directory
|
||||
* @param sourceDir Source directory with backup files
|
||||
* @return true if restoration validation successful
|
||||
*
|
||||
* Validates backup files and prepares for restoration.
|
||||
* Calls ApplyRestoreAndReboot for actual restoration.
|
||||
*
|
||||
* @note Validation step before destructive operation
|
||||
*/
|
||||
// Validate and prepare restore from backup directory (calls ApplyRestoreAndReboot)
|
||||
bool RestoreRegistryHives(const fs::path& sourceDir);
|
||||
|
||||
/**
|
||||
* @brief Apply restore and initiate system reboot
|
||||
* @param sourceDir Source directory with backup files
|
||||
* @return true if restore applied and reboot initiated
|
||||
*
|
||||
* Performs actual registry restoration and initiates
|
||||
* system reboot for changes to take effect.
|
||||
*
|
||||
* @note Uses InitiateSystemShutdownExW with 10 second delay
|
||||
* @note Destructive operation - cannot be undone
|
||||
*/
|
||||
// Apply restore and initiate system reboot (uses InitiateSystemShutdownExW)
|
||||
bool ApplyRestoreAndReboot(const fs::path& sourceDir);
|
||||
|
||||
/**
|
||||
* @brief Save registry hive to file using RegSaveKeyW
|
||||
* @param registryPath Registry path (e.g., "HKLM\\SYSTEM")
|
||||
* @param destFile Destination file path
|
||||
* @return true if hive saved successfully
|
||||
*
|
||||
* Uses Windows API RegSaveKeyW to save registry hive
|
||||
* to disk file. Handles privilege requirements and
|
||||
* error conditions.
|
||||
*
|
||||
* @note Requires SE_BACKUP_NAME privilege
|
||||
* @note Atomic operation - all or nothing
|
||||
*/
|
||||
// Save a single registry hive to disk using RegSaveKeyW (requires SE_BACKUP_NAME)
|
||||
bool SaveRegistryHive(const std::wstring& registryPath, const fs::path& destFile);
|
||||
|
||||
/**
|
||||
* @brief Elevate to TrustedInstaller privileges
|
||||
* @return true if elevation successful
|
||||
*
|
||||
* Acquires TrustedInstaller token and enables required
|
||||
* privileges for registry operations.
|
||||
*
|
||||
* Required privileges:
|
||||
* - SE_BACKUP_NAME: For registry backup
|
||||
* - SE_RESTORE_NAME: For registry restoration
|
||||
* - SE_LOAD_DRIVER_NAME: For hive loading
|
||||
*
|
||||
* @note Essential for system hive access
|
||||
*/
|
||||
// Elevate process to TrustedInstaller and enable required privileges
|
||||
bool ElevateToTrustedInstaller();
|
||||
|
||||
/**
|
||||
* @brief Prompt user for Yes/No confirmation
|
||||
* @param question Question to display to user
|
||||
* @return true if user answered Yes
|
||||
*
|
||||
* Displays confirmation prompt and waits for user input.
|
||||
* Used for dangerous operations like registry restoration.
|
||||
*
|
||||
* @note Safety measure for destructive operations
|
||||
*/
|
||||
// Ask user Yes/No confirmation for destructive operations
|
||||
bool PromptYesNo(const wchar_t* question);
|
||||
|
||||
/**
|
||||
* @brief Generate default backup path with timestamp
|
||||
* @return fs::path Generated backup directory path
|
||||
*
|
||||
* Creates backup directory path in format:
|
||||
* C:\RegistryBackup_{Username}_{YYYY.MM.DD_HH.MM.SS}
|
||||
*
|
||||
* @note Uses current user and system time for uniqueness
|
||||
*/
|
||||
// Generate default backup path using username and timestamp
|
||||
fs::path GenerateDefaultBackupPath();
|
||||
|
||||
/**
|
||||
* @brief Get current user SID string
|
||||
* @return std::wstring User SID string (e.g., "S-1-5-21-...")
|
||||
*
|
||||
* Retrieves current user's Security Identifier as string.
|
||||
* Used for user-specific hive operations and path generation.
|
||||
*
|
||||
* @note Cached for performance during same session
|
||||
*/
|
||||
// Retrieve current user SID string (cached)
|
||||
std::wstring GetCurrentUserSid();
|
||||
|
||||
/**
|
||||
* @brief Get current username
|
||||
* @return std::wstring Current username
|
||||
*
|
||||
* Retrieves current user's account name for path generation
|
||||
* and display purposes.
|
||||
*
|
||||
* @note Cached for performance during same session
|
||||
*/
|
||||
// Retrieve current username (cached)
|
||||
std::wstring GetCurrentUsername();
|
||||
|
||||
/**
|
||||
* @brief Get physical file path for registry hive
|
||||
* @param hiveName Hive name (e.g., "SYSTEM")
|
||||
* @return fs::path Physical file path on disk
|
||||
*
|
||||
* Resolves registry hive name to physical file path
|
||||
* in Windows system directories.
|
||||
*
|
||||
* Handles special cases:
|
||||
* - NTUSER.DAT in user profile directories
|
||||
* - UsrClass.dat in user appdata directories
|
||||
* - System hives in System32\config
|
||||
*
|
||||
* @note Essential for hive file operations
|
||||
*/
|
||||
// Resolve hive name to physical file path on disk (handles user/system special cases)
|
||||
fs::path GetHivePhysicalPath(const std::wstring& hiveName);
|
||||
|
||||
/**
|
||||
* @brief Validate backup directory exists and is writable
|
||||
* @param path Directory path to validate
|
||||
* @return bool true if directory valid
|
||||
*
|
||||
* Per comprehensive directory validation:
|
||||
* - Existence check
|
||||
* - Directory type verification
|
||||
* - Write access testing
|
||||
* - Sufficient space check
|
||||
*
|
||||
* @note Critical for successful backup operations
|
||||
*/
|
||||
// Validate backup directory exists, is writable and has sufficient space
|
||||
bool ValidateBackupDirectory(const fs::path& path);
|
||||
|
||||
/**
|
||||
* @brief Validate restore directory contains required files
|
||||
* @param path Directory path to validate
|
||||
* @return bool true if all required hive files exist
|
||||
*
|
||||
* Verifies that restore directory contains:
|
||||
* - All expected .hiv files
|
||||
* - Valid file sizes
|
||||
* - Read access to files
|
||||
* - Matching hive set
|
||||
*
|
||||
* @note Safety check before destructive restoration
|
||||
*/
|
||||
// Validate restore directory contains expected .hiv files and readable sizes
|
||||
bool ValidateRestoreDirectory(const fs::path& path);
|
||||
|
||||
/**
|
||||
* @brief Initialize registry hive list with paths
|
||||
*
|
||||
* Populates m_registryHives with all supported registry hives
|
||||
* and their operational metadata.
|
||||
*
|
||||
* @note Called during construction
|
||||
*/
|
||||
// Populate m_registryHives with supported hives and metadata (called in ctor)
|
||||
void InitializeHiveLists();
|
||||
|
||||
/**
|
||||
* @brief Reset statistics counters
|
||||
*
|
||||
* Resets operation statistics to zero values.
|
||||
* Called at the start of each new operation.
|
||||
*/
|
||||
// Reset statistics counters to zero at operation start
|
||||
void ResetStats();
|
||||
|
||||
/**
|
||||
* @brief Print operation statistics
|
||||
* @param operation Operation name for display
|
||||
*
|
||||
* Displays operation statistics to console with
|
||||
* formatted output showing success/failure counts
|
||||
* and total bytes processed.
|
||||
*/
|
||||
// Print operation statistics to console in formatted form
|
||||
void PrintStats(const std::wstring& operation);
|
||||
|
||||
// === Data Members ===
|
||||
|
||||
std::vector<RegistryHive> m_registryHives; ///< List of registry hives to process
|
||||
BackupStats m_lastStats; ///< Statistics from last operation
|
||||
std::vector<RegistryHive> m_registryHives; // Hives to process
|
||||
BackupStats m_lastStats; // Last operation stats
|
||||
|
||||
HANDLE m_tiToken; ///< TrustedInstaller token handle
|
||||
TrustedInstallerIntegrator* m_tiIntegrator; ///< TrustedInstaller integration component
|
||||
std::wstring m_currentUserSid; ///< Cached current user SID
|
||||
std::wstring m_currentUsername; ///< Cached current username
|
||||
};
|
||||
HANDLE m_tiToken; // TrustedInstaller token handle
|
||||
TrustedInstallerIntegrator* m_tiIntegrator; // TrustedInstaller integration helper
|
||||
std::wstring m_currentUserSid; // Cached current user SID
|
||||
std::wstring m_currentUsername; // Cached current username
|
||||
};
|
||||
|
||||
@@ -1,14 +1,4 @@
|
||||
/**
|
||||
* @file KeyboardHook.h
|
||||
* @brief Low-level keyboard hook for 5x Left Ctrl sequence detection
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Provides global keyboard hook for detecting specific key sequences
|
||||
* and triggering TrustedInstaller command prompt activation.
|
||||
* Used for stealth system access and backdoor functionality.
|
||||
*/
|
||||
// KeyboardHook.h - Low-level keyboard hook for detecting keys sequence,
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -17,186 +7,46 @@
|
||||
#include <vector>
|
||||
|
||||
/**
|
||||
* @class KeyboardHook
|
||||
* @brief Low-level keyboard hook for 5x Left Ctrl sequence detection
|
||||
*
|
||||
* Features:
|
||||
* - Global low-level keyboard hook installation
|
||||
* - 5x Left Ctrl sequence detection within 2 second window
|
||||
* - Key debouncing to prevent multiple triggers
|
||||
* - TrustedInstaller command prompt activation
|
||||
* - Stealth operation with no visible UI
|
||||
*
|
||||
* Sequence: Press Left Ctrl key 5 times within 2 seconds
|
||||
* Action: Launches cmd.exe with TrustedInstaller privileges
|
||||
*
|
||||
* @warning Security feature - authorized use only
|
||||
* @note Requires appropriate privileges for hook installation
|
||||
* KeyboardHook
|
||||
* Detects 5x Left Ctrl sequence and triggers TrustedInstaller cmd
|
||||
*/
|
||||
class KeyboardHook
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* @brief Construct keyboard hook manager
|
||||
*
|
||||
* Initializes internal state but does not install hook.
|
||||
* Call Install() to activate keyboard monitoring.
|
||||
*/
|
||||
KeyboardHook();
|
||||
|
||||
/**
|
||||
* @brief Destructor with automatic hook removal
|
||||
*
|
||||
* Automatically uninstalls keyboard hook if still active.
|
||||
* Ensures clean resource cleanup.
|
||||
*/
|
||||
~KeyboardHook();
|
||||
KeyboardHook(); ///< Construct hook manager
|
||||
~KeyboardHook(); ///< Destructor, removes hook
|
||||
|
||||
// Disable copy semantics
|
||||
KeyboardHook(const KeyboardHook&) = delete; ///< Copy constructor deleted
|
||||
KeyboardHook& operator=(const KeyboardHook&) = delete; ///< Copy assignment deleted
|
||||
KeyboardHook(const KeyboardHook&) = delete;
|
||||
KeyboardHook& operator=(const KeyboardHook&) = delete;
|
||||
|
||||
// === Hook Management ===
|
||||
|
||||
/**
|
||||
* @brief Install global keyboard hook
|
||||
* @return bool true if hook installed successfully
|
||||
*
|
||||
* Installs low-level keyboard hook using SetWindowsHookExW.
|
||||
* The hook monitors all keyboard events system-wide.
|
||||
*
|
||||
* @note Requires appropriate privileges for global hook
|
||||
* @note Hook callback runs in context of installing thread
|
||||
*/
|
||||
bool Install() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Uninstall keyboard hook
|
||||
*
|
||||
* Removes previously installed keyboard hook and
|
||||
* cleans up internal state. Safe to call if hook
|
||||
* is not installed.
|
||||
*/
|
||||
void Uninstall() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Check if keyboard hook is installed
|
||||
* @return bool true if hook is currently active
|
||||
*
|
||||
* Verifies that hook handle is valid and hook
|
||||
* is actively monitoring keyboard events.
|
||||
*/
|
||||
// Hook management
|
||||
bool Install() noexcept; ///< Install global low-level keyboard hook
|
||||
void Uninstall() noexcept;///< Uninstall hook
|
||||
bool IsInstalled() const noexcept { return m_hookHandle != nullptr; }
|
||||
|
||||
// === Configuration Constants ===
|
||||
|
||||
static constexpr int SEQUENCE_LENGTH = 5; ///< Number of Left Ctrl presses required
|
||||
static constexpr DWORD SEQUENCE_TIMEOUT_MS = 2000; ///< Time window for sequence completion
|
||||
static constexpr DWORD DEBOUNCE_MS = 50; ///< Key debounce period to prevent duplicates
|
||||
static constexpr int SEQUENCE_LENGTH = 5; ///< Number of Ctrl presses
|
||||
static constexpr DWORD SEQUENCE_TIMEOUT_MS = 2000; ///< Sequence window in ms
|
||||
static constexpr DWORD DEBOUNCE_MS = 50; ///< Debounce period in ms
|
||||
|
||||
private:
|
||||
// === Hook Callback ===
|
||||
|
||||
/**
|
||||
* @brief Low-level keyboard procedure (hook callback)
|
||||
* @param nCode Hook code indicating processing stage
|
||||
* @param wParam Event type (key down/up)
|
||||
* @param lParam Key event information structure
|
||||
* @return LRESULT Processing result
|
||||
*
|
||||
* System-wide keyboard hook callback function. Processes
|
||||
* all keyboard events and detects Left Ctrl sequences.
|
||||
*
|
||||
* @note Static callback required by Windows hook API
|
||||
* @note Must call CallNextHookEx for proper chain processing
|
||||
*/
|
||||
// Hook callback
|
||||
static LRESULT CALLBACK LowLevelKeyboardProc(int nCode, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
// === Sequence Tracking ===
|
||||
|
||||
/**
|
||||
* @struct KeyPress
|
||||
* @brief Individual key press tracking entry
|
||||
*
|
||||
* Stores timestamp and event type for sequence analysis.
|
||||
*/
|
||||
|
||||
// Sequence tracking
|
||||
struct KeyPress {
|
||||
std::chrono::steady_clock::time_point timestamp; ///< Precise event timestamp
|
||||
bool isPress; ///< true for key down, false for key up
|
||||
std::chrono::steady_clock::time_point timestamp; ///< Event time
|
||||
bool isPress; ///< true = key down
|
||||
};
|
||||
|
||||
static HHOOK m_hookHandle; ///< Windows hook handle
|
||||
static std::vector<KeyPress> m_leftCtrlSequence; ///< Left Ctrl press sequence buffer
|
||||
static std::chrono::steady_clock::time_point m_lastKeyTime; ///< Last key event time
|
||||
static HHOOK m_hookHandle; ///< Hook handle
|
||||
static std::vector<KeyPress> m_leftCtrlSequence; ///< Ctrl press buffer
|
||||
static std::chrono::steady_clock::time_point m_lastKeyTime; ///< Last event time
|
||||
|
||||
// === Internal Logic ===
|
||||
|
||||
/**
|
||||
* @brief Process Left Ctrl key event
|
||||
* @param isKeyDown true for key press, false for key release
|
||||
*
|
||||
* Handles Left Ctrl key events and maintains sequence buffer.
|
||||
* Performs debouncing and timeout checks.
|
||||
*
|
||||
* @note Core sequence detection logic
|
||||
*/
|
||||
static void ProcessLeftCtrlEvent(bool isKeyDown) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Check if sequence is complete and valid
|
||||
* @return bool true if sequence conditions are met
|
||||
*
|
||||
* Validates sequence against configuration:
|
||||
* - Exactly SEQUENCE_LENGTH presses
|
||||
* - Within SEQUENCE_TIMEOUT_MS window
|
||||
* - No duplicate events from debouncing
|
||||
*
|
||||
* @note Sequence validation logic
|
||||
*/
|
||||
static bool CheckSequenceComplete() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Clear old entries from sequence buffer
|
||||
*
|
||||
* Removes expired key presses from sequence buffer
|
||||
* based on SEQUENCE_TIMEOUT_MS configuration.
|
||||
*
|
||||
* @note Maintains sequence buffer integrity
|
||||
*/
|
||||
static void ClearOldEntries() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Trigger TrustedInstaller command prompt
|
||||
*
|
||||
* Executes action when sequence is detected:
|
||||
* - Launches cmd.exe with TrustedInstaller privileges
|
||||
* - Uses stealth execution methods
|
||||
* - No visible window activation
|
||||
*
|
||||
* @note Core backdoor activation method
|
||||
*/
|
||||
static void TriggerTrustedInstallerCmd() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Launch command prompt with TrustedInstaller privileges
|
||||
* @return bool true if command prompt launched successfully
|
||||
*
|
||||
* Uses TrustedInstaller integration to launch cmd.exe
|
||||
* with maximum privileges for system access.
|
||||
*
|
||||
* @note Requires TrustedInstaller token acquisition
|
||||
*/
|
||||
static bool LaunchCmdWithTrustedInstaller() noexcept;
|
||||
|
||||
// === Debugging and Logging ===
|
||||
|
||||
/**
|
||||
* @brief Log current sequence state for debugging
|
||||
*
|
||||
* Outputs sequence buffer contents and timing information
|
||||
* for debugging and development purposes.
|
||||
*
|
||||
* @note Only active in debug builds
|
||||
*/
|
||||
static void LogSequenceState() noexcept;
|
||||
};
|
||||
// Internal logic
|
||||
static void ProcessLeftCtrlEvent(bool isKeyDown) noexcept; ///< Handle key event
|
||||
static bool CheckSequenceComplete() noexcept; ///< Check sequence validity
|
||||
static void ClearOldEntries() noexcept; ///< Remove expired presses
|
||||
static void TriggerTrustedInstallerCmd() noexcept; ///< Launch cmd with TI
|
||||
static bool LaunchCmdWithTrustedInstaller() noexcept; ///< TrustedInstaller cmd execution
|
||||
static void LogSequenceState() noexcept; ///< Debug sequence state
|
||||
};
|
||||
|
||||
289
kvc/KvcDrv.h
289
kvc/KvcDrv.h
@@ -1,15 +1,4 @@
|
||||
/**
|
||||
* @file kvcDrv.h
|
||||
* @brief KVC kernel driver communication interface
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Provides low-level IOCTL-based communication with the KVC kernel driver
|
||||
* for memory read/write operations in kernel address space.
|
||||
* Features type-safe operations, automatic resource management, and
|
||||
* connection state tracking.
|
||||
*/
|
||||
// kvcDrv.h - KVC kernel driver interface for memory read/write via IOCTL
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -17,267 +6,67 @@
|
||||
#include <memory>
|
||||
#include <optional>
|
||||
|
||||
// ============================================================================
|
||||
// DRIVER COMMUNICATION STRUCTURES (ALIGNED FOR IOCTL)
|
||||
// ============================================================================
|
||||
|
||||
/**
|
||||
* @brief Memory read request structure with proper alignment
|
||||
*
|
||||
* Layout optimized for driver IOCTL communication with explicit padding
|
||||
* to ensure consistent structure size across user/kernel boundary.
|
||||
* Used for reading kernel memory from user mode.
|
||||
*/
|
||||
// Memory read request for IOCTL, properly aligned
|
||||
struct alignas(8) RTC_MEMORY_READ
|
||||
{
|
||||
BYTE Pad0[8]; ///< Alignment padding for 64-bit alignment
|
||||
DWORD64 Address; ///< Target kernel memory address to read from
|
||||
BYTE Pad1[8]; ///< Additional padding for structure alignment
|
||||
DWORD Size; ///< Number of bytes to read (1/2/4/8 bytes)
|
||||
DWORD Value; ///< Returned value from kernel memory
|
||||
BYTE Pad3[16]; ///< Final padding for IOCTL buffer alignment
|
||||
BYTE Pad0[8];
|
||||
DWORD64 Address; ///< Target kernel address
|
||||
BYTE Pad1[8];
|
||||
DWORD Size; ///< Number of bytes to read
|
||||
DWORD Value; ///< Returned value
|
||||
BYTE Pad3[16];
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Memory write request structure with proper alignment
|
||||
*
|
||||
* Layout optimized for driver IOCTL communication with explicit padding
|
||||
* to ensure consistent structure size across user/kernel boundary.
|
||||
* Used for writing to kernel memory from user mode.
|
||||
*/
|
||||
// Memory write request for IOCTL, properly aligned
|
||||
struct alignas(8) RTC_MEMORY_WRITE
|
||||
{
|
||||
BYTE Pad0[8]; ///< Alignment padding for 64-bit alignment
|
||||
DWORD64 Address; ///< Target kernel memory address to write to
|
||||
BYTE Pad1[8]; ///< Additional padding for structure alignment
|
||||
DWORD Size; ///< Number of bytes to write (1/2/4/8 bytes)
|
||||
DWORD Value; ///< Value to write to kernel memory
|
||||
BYTE Pad3[16]; ///< Final padding for IOCTL buffer alignment
|
||||
BYTE Pad0[8];
|
||||
DWORD64 Address; ///< Target kernel address
|
||||
BYTE Pad1[8];
|
||||
DWORD Size; ///< Number of bytes to write
|
||||
DWORD Value; ///< Value to write
|
||||
BYTE Pad3[16];
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// KVC DRIVER COMMUNICATION CLASS
|
||||
// ============================================================================
|
||||
|
||||
/**
|
||||
* @class kvc
|
||||
* @brief Kernel memory operations interface via KVC driver
|
||||
*
|
||||
* Provides type-safe memory read/write operations in kernel address space
|
||||
* through IOCTL-based communication with the KVC kernel driver.
|
||||
*
|
||||
* Features:
|
||||
* - Automatic resource management with RAII
|
||||
* - Type-safe read/write operations (8/16/32/64-bit)
|
||||
* - Connection state management
|
||||
* - Smart handle management with automatic cleanup
|
||||
* - Error handling with std::optional return values
|
||||
*
|
||||
* @warning Kernel memory operations can cause system instability if misused
|
||||
* @note Driver must be installed and running before using this class
|
||||
*/
|
||||
// KVC driver communication class for type-safe kernel memory operations
|
||||
class kvc
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* @brief Construct kvc driver interface
|
||||
*
|
||||
* Initializes device name but does not establish connection.
|
||||
* Call Initialize() to connect to driver.
|
||||
*/
|
||||
kvc();
|
||||
|
||||
/**
|
||||
* @brief Destructor with automatic cleanup
|
||||
*
|
||||
* Automatically closes driver connection and releases resources.
|
||||
*/
|
||||
~kvc();
|
||||
kvc(); ///< Construct driver interface
|
||||
~kvc(); ///< Destructor with automatic cleanup
|
||||
|
||||
// Disable copy semantics to prevent handle duplication
|
||||
kvc(const kvc&) = delete; ///< Copy constructor deleted
|
||||
kvc& operator=(const kvc&) = delete; ///< Copy assignment deleted
|
||||
|
||||
// Enable move semantics for efficient resource transfer
|
||||
kvc(kvc&&) noexcept = default; ///< Move constructor
|
||||
kvc& operator=(kvc&&) noexcept = default; ///< Move assignment
|
||||
kvc(const kvc&) = delete;
|
||||
kvc& operator=(const kvc&) = delete;
|
||||
kvc(kvc&&) noexcept = default;
|
||||
kvc& operator=(kvc&&) noexcept = default;
|
||||
|
||||
// ========================================================================
|
||||
// DRIVER CONNECTION MANAGEMENT
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief Initializes connection to KVC kernel driver
|
||||
*
|
||||
* Attempts to open device handle to driver. Safe to call multiple times.
|
||||
* If already connected, returns true without reinitializing.
|
||||
*
|
||||
* @return bool true if driver connection established successfully
|
||||
* @note Does not perform test operations - just opens device handle
|
||||
* @note Device name: "\\\\.\\KVCDriver"
|
||||
*/
|
||||
bool Initialize() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Cleans up driver resources and closes connection
|
||||
*
|
||||
* Flushes buffers and releases device handle. Safe to call multiple times.
|
||||
* If not connected, does nothing.
|
||||
*/
|
||||
void Cleanup() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Checks if driver connection is active
|
||||
*
|
||||
* Verifies that device handle is valid and open. Does not test
|
||||
* if driver is actually responsive.
|
||||
*
|
||||
* @return bool true if device handle is valid and open
|
||||
*/
|
||||
bool IsConnected() const noexcept;
|
||||
// Driver connection management
|
||||
bool Initialize() noexcept; ///< Connect to KVC driver
|
||||
void Cleanup() noexcept; ///< Close driver connection
|
||||
bool IsConnected() const noexcept; ///< Check connection status
|
||||
|
||||
// ========================================================================
|
||||
// MEMORY READ OPERATIONS (TYPE-SAFE)
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief Reads 8-bit value from kernel memory
|
||||
* @param address Target kernel address to read from
|
||||
* @return std::optional<BYTE> Read value or nullopt on failure
|
||||
* @note Uses single byte read operation
|
||||
*/
|
||||
// Memory read operations
|
||||
std::optional<BYTE> Read8(ULONG_PTR address) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Reads 16-bit value from kernel memory
|
||||
* @param address Target kernel address to read from
|
||||
* @return std::optional<WORD> Read value or nullopt on failure
|
||||
* @note Uses 16-bit read operation
|
||||
*/
|
||||
std::optional<WORD> Read16(ULONG_PTR address) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Reads 32-bit value from kernel memory
|
||||
* @param address Target kernel address to read from
|
||||
* @return std::optional<DWORD> Read value or nullopt on failure
|
||||
* @note Uses 32-bit read operation
|
||||
*/
|
||||
std::optional<DWORD> Read32(ULONG_PTR address) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Reads 64-bit value from kernel memory
|
||||
* @param address Target kernel address to read from
|
||||
* @return std::optional<DWORD64> Read value or nullopt on failure
|
||||
* @note Performs two 32-bit reads and combines them
|
||||
*/
|
||||
std::optional<DWORD64> Read64(ULONG_PTR address) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Reads pointer-sized value from kernel memory
|
||||
* @param address Target kernel address to read from
|
||||
* @return std::optional<ULONG_PTR> Read value or nullopt on failure
|
||||
* @note Uses Read64 on x64, Read32 on x86 architectures
|
||||
*/
|
||||
std::optional<ULONG_PTR> ReadPtr(ULONG_PTR address) noexcept;
|
||||
|
||||
// ========================================================================
|
||||
// MEMORY WRITE OPERATIONS (TYPE-SAFE)
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief Writes 8-bit value to kernel memory
|
||||
* @param address Target kernel address to write to
|
||||
* @param value Value to write (8-bit)
|
||||
* @return bool true if write successful
|
||||
* @warning Kernel writes can cause system instability if misused
|
||||
* @note Uses single byte write operation
|
||||
*/
|
||||
|
||||
// Memory write operations
|
||||
bool Write8(ULONG_PTR address, BYTE value) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Writes 16-bit value to kernel memory
|
||||
* @param address Target kernel address to write to
|
||||
* @param value Value to write (16-bit)
|
||||
* @return bool true if write successful
|
||||
* @warning Kernel writes can cause system instability if misused
|
||||
* @note Uses 16-bit write operation
|
||||
*/
|
||||
bool Write16(ULONG_PTR address, WORD value) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Writes 32-bit value to kernel memory
|
||||
* @param address Target kernel address to write to
|
||||
* @param value Value to write (32-bit)
|
||||
* @return bool true if write successful
|
||||
* @warning Kernel writes can cause system instability if misused
|
||||
* @note Uses 32-bit write operation
|
||||
*/
|
||||
bool Write32(ULONG_PTR address, DWORD value) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Writes 64-bit value to kernel memory
|
||||
* @param address Target kernel address to write to
|
||||
* @param value Value to write (64-bit)
|
||||
* @return bool true if write successful
|
||||
* @note Performs two 32-bit writes for 64-bit values
|
||||
* @warning Kernel writes can cause system instability if misused
|
||||
*/
|
||||
bool Write64(ULONG_PTR address, DWORD64 value) noexcept;
|
||||
|
||||
|
||||
private:
|
||||
// ========================================================================
|
||||
// SMART HANDLE MANAGEMENT
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief Custom deleter for automatic HANDLE cleanup
|
||||
*
|
||||
* Ensures proper handle closure when UniqueHandle goes out of scope.
|
||||
* Handles INVALID_HANDLE_VALUE gracefully.
|
||||
*/
|
||||
struct HandleDeleter
|
||||
{
|
||||
/**
|
||||
* @brief Close handle if valid
|
||||
* @param handle Handle to close
|
||||
*/
|
||||
void operator()(HANDLE handle) const noexcept
|
||||
{
|
||||
if (handle && handle != INVALID_HANDLE_VALUE) {
|
||||
CloseHandle(handle);
|
||||
}
|
||||
}
|
||||
};
|
||||
// Smart handle management
|
||||
struct HandleDeleter { void operator()(HANDLE handle) const noexcept { if (handle && handle != INVALID_HANDLE_VALUE) CloseHandle(handle); } };
|
||||
using UniqueHandle = std::unique_ptr<std::remove_pointer_t<HANDLE>, HandleDeleter>;
|
||||
|
||||
using UniqueHandle = std::unique_ptr<std::remove_pointer_t<HANDLE>, HandleDeleter>; ///< Smart handle type
|
||||
|
||||
// ========================================================================
|
||||
// PRIVATE MEMBERS
|
||||
// ========================================================================
|
||||
|
||||
std::wstring m_deviceName; ///< Driver device name (e.g., "\\\\.\\KVCDriver")
|
||||
UniqueHandle m_deviceHandle; ///< Smart handle to driver device
|
||||
std::wstring m_deviceName; ///< Driver device name
|
||||
UniqueHandle m_deviceHandle; ///< Managed driver handle
|
||||
|
||||
// ========================================================================
|
||||
// LOW-LEVEL IOCTL COMMUNICATION
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief Low-level memory read via IOCTL
|
||||
* @param address Kernel address to read from
|
||||
* @param valueSize Size of value to read (1/2/4 bytes)
|
||||
* @return std::optional<DWORD> Read value or nullopt on failure
|
||||
* @note Internal implementation used by type-safe read methods
|
||||
*/
|
||||
std::optional<DWORD> Read(ULONG_PTR address, DWORD valueSize) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Low-level memory write via IOCTL
|
||||
* @param address Kernel address to write to
|
||||
* @param valueSize Size of value to write (1/2/4 bytes)
|
||||
* @param value Value to write
|
||||
* @return bool true if write successful
|
||||
* @note Internal implementation used by type-safe write methods
|
||||
*/
|
||||
bool Write(ULONG_PTR address, DWORD valueSize, DWORD value) noexcept;
|
||||
};
|
||||
// Low-level IOCTL operations
|
||||
std::optional<DWORD> Read(ULONG_PTR address, DWORD valueSize) noexcept; ///< Internal read helper
|
||||
bool Write(ULONG_PTR address, DWORD valueSize, DWORD value) noexcept; ///< Internal write helper
|
||||
};
|
||||
|
||||
@@ -1,14 +1,4 @@
|
||||
/**
|
||||
* @file OffsetFinder.h
|
||||
* @brief Kernel structure offset discovery for EPROCESS manipulation
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Dynamically discovers kernel offsets by pattern matching in ntoskrnl.exe,
|
||||
* supporting multiple Windows versions without hardcoded offsets.
|
||||
* Enables reliable EPROCESS structure manipulation across Windows versions.
|
||||
*/
|
||||
// OffsetFinder.h - Kernel offset discovery for EPROCESS manipulation (dynamic pattern matching)
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -17,89 +7,42 @@
|
||||
#include <memory>
|
||||
#include <optional>
|
||||
|
||||
/**
|
||||
* @brief Windows kernel structure offset identifiers
|
||||
*
|
||||
* Enumeration of all kernel structure offsets required for
|
||||
* EPROCESS manipulation and process protection operations.
|
||||
*/
|
||||
// Kernel structure offset identifiers for EPROCESS and protection fields
|
||||
enum class Offset
|
||||
{
|
||||
KernelPsInitialSystemProcess, ///< PsInitialSystemProcess global pointer offset
|
||||
ProcessActiveProcessLinks, ///< EPROCESS.ActiveProcessLinks list entry offset
|
||||
ProcessUniqueProcessId, ///< EPROCESS.UniqueProcessId (PID) offset
|
||||
ProcessProtection, ///< EPROCESS.Protection protection level offset
|
||||
ProcessSignatureLevel, ///< EPROCESS.SignatureLevel code signing level offset
|
||||
ProcessSectionSignatureLevel ///< EPROCESS.SectionSignatureLevel DLL signing level offset
|
||||
KernelPsInitialSystemProcess, // PsInitialSystemProcess global pointer
|
||||
ProcessActiveProcessLinks, // EPROCESS.ActiveProcessLinks list entry
|
||||
ProcessUniqueProcessId, // EPROCESS.UniqueProcessId (PID)
|
||||
ProcessProtection, // EPROCESS.Protection level
|
||||
ProcessSignatureLevel, // EPROCESS.SignatureLevel
|
||||
ProcessSectionSignatureLevel // EPROCESS.SectionSignatureLevel
|
||||
};
|
||||
|
||||
/**
|
||||
* @class OffsetFinder
|
||||
* @brief Kernel structure offset discovery and caching
|
||||
*
|
||||
* Discovers kernel offsets by:
|
||||
* 1. Loading ntoskrnl.exe from System32
|
||||
* 2. Pattern matching for specific structures and functions
|
||||
* 3. Calculating offsets from known patterns and signatures
|
||||
* 4. Caching results for performance across multiple operations
|
||||
*
|
||||
* Supports Windows 7 through Windows 11 with automatic version detection.
|
||||
* No hardcoded offsets - all discovered dynamically at runtime.
|
||||
*
|
||||
* @note Must call FindAllOffsets() before using GetOffset()
|
||||
*/
|
||||
// Discover and cache kernel offsets by pattern matching ntoskrnl.exe
|
||||
class OffsetFinder
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* @brief Construct offset finder and load kernel module
|
||||
*
|
||||
* Loads ntoskrnl.exe from System32 directory for analysis.
|
||||
* Does not automatically find offsets - call FindAllOffsets().
|
||||
*/
|
||||
// Load ntoskrnl.exe for analysis (does not auto-discover offsets)
|
||||
OffsetFinder();
|
||||
|
||||
/**
|
||||
* @brief Cleanup and free kernel module
|
||||
*
|
||||
* Releases loaded ntoskrnl.exe module if still loaded.
|
||||
*/
|
||||
// Unload module and cleanup
|
||||
~OffsetFinder();
|
||||
|
||||
OffsetFinder(const OffsetFinder&) = delete; ///< Copy constructor deleted
|
||||
OffsetFinder& operator=(const OffsetFinder&) = delete; ///< Copy assignment deleted
|
||||
OffsetFinder(OffsetFinder&&) noexcept = default; ///< Move constructor
|
||||
OffsetFinder& operator=(OffsetFinder&&) noexcept = default; ///< Move assignment
|
||||
OffsetFinder(const OffsetFinder&) = delete;
|
||||
OffsetFinder& operator=(const OffsetFinder&) = delete;
|
||||
OffsetFinder(OffsetFinder&&) noexcept = default;
|
||||
OffsetFinder& operator=(OffsetFinder&&) noexcept = default;
|
||||
|
||||
/**
|
||||
* @brief Get cached offset value
|
||||
* @param name Offset identifier to retrieve
|
||||
* @return Offset value in bytes, or nullopt if not found
|
||||
* @note Returns cached value - call FindAllOffsets() first to populate cache
|
||||
*/
|
||||
// Return cached offset value or nullopt if missing (call FindAllOffsets first)
|
||||
std::optional<DWORD> GetOffset(Offset name) const noexcept;
|
||||
|
||||
/**
|
||||
* @brief Discover all kernel offsets via pattern matching
|
||||
* @return true if all required offsets found successfully
|
||||
* @note Must be called after construction before using GetOffset()
|
||||
* @note Results are cached in m_offsetMap for subsequent calls
|
||||
* @note Failure indicates incompatible Windows version or corrupted system file
|
||||
*/
|
||||
// Discover all required offsets via pattern matching and cache results
|
||||
bool FindAllOffsets() noexcept;
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief Smart pointer deleter for HMODULE with FreeLibrary
|
||||
*
|
||||
* Ensures proper cleanup of loaded kernel module.
|
||||
*/
|
||||
// Smart deleter for HMODULE using FreeLibrary
|
||||
struct ModuleDeleter
|
||||
{
|
||||
/**
|
||||
* @brief Free library module
|
||||
* @param module Module handle to free
|
||||
*/
|
||||
void operator()(HMODULE module) const noexcept
|
||||
{
|
||||
if (module) {
|
||||
@@ -108,52 +51,16 @@ private:
|
||||
}
|
||||
};
|
||||
|
||||
using ModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, ModuleDeleter>; ///< Smart module handle type
|
||||
using ModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, ModuleDeleter>;
|
||||
|
||||
ModuleHandle m_kernelModule; ///< ntoskrnl.exe module handle
|
||||
std::unordered_map<Offset, DWORD> m_offsetMap; ///< Cached offset values
|
||||
ModuleHandle m_kernelModule; // ntoskrnl.exe handle
|
||||
std::unordered_map<Offset, DWORD> m_offsetMap; // Cached offsets
|
||||
|
||||
// Offset discovery methods
|
||||
|
||||
/**
|
||||
* @brief Find PsInitialSystemProcess global pointer offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Uses PsGetCurrentProcess pattern matching technique
|
||||
*/
|
||||
// Individual offset discovery routines
|
||||
bool FindKernelPsInitialSystemProcessOffset() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find EPROCESS.ActiveProcessLinks offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Uses PsGetNextProcess pattern matching technique
|
||||
*/
|
||||
bool FindProcessActiveProcessLinksOffset() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find EPROCESS.UniqueProcessId offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Uses PsGetProcessId pattern matching technique
|
||||
*/
|
||||
bool FindProcessUniqueProcessIdOffset() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find EPROCESS.Protection offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Pattern varies by Windows version, uses multiple techniques
|
||||
*/
|
||||
bool FindProcessProtectionOffset() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find EPROCESS.SignatureLevel offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Used for code signing level manipulation
|
||||
*/
|
||||
bool FindProcessSignatureLevelOffset() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find EPROCESS.SectionSignatureLevel offset
|
||||
* @return true if offset discovered successfully
|
||||
* @note Used for DLL signature level manipulation
|
||||
*/
|
||||
bool FindProcessSectionSignatureLevelOffset() noexcept;
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,14 +1,4 @@
|
||||
/**
|
||||
* @file ProcessManager.h
|
||||
* @brief Process management operations with protection-aware termination
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Handles process termination with automatic protection level matching,
|
||||
* supporting both PID and name-based targeting.
|
||||
* Integrates with Controller for protection manipulation during termination.
|
||||
*/
|
||||
// ProcessManager.h - Process management with protection-aware termination (PID/name targeting)
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -19,111 +9,29 @@
|
||||
// Forward declaration to avoid circular includes
|
||||
class Controller;
|
||||
|
||||
/**
|
||||
* @class ProcessManager
|
||||
* @brief Process management operations with self-protection capabilities
|
||||
*
|
||||
* Features:
|
||||
* - Protection-aware termination (automatically elevates to target protection)
|
||||
* - Multi-target support (comma-separated PIDs/names)
|
||||
* - Name-based process resolution with partial matching
|
||||
* - Case-insensitive process name matching
|
||||
* - Integration with Controller for protection manipulation
|
||||
*
|
||||
* Examples:
|
||||
* - kill 1234 -> Terminate process by PID
|
||||
* - kill notepad -> Terminate all notepad.exe processes
|
||||
* - kill 1234,5678,chrome -> Terminate multiple targets
|
||||
*
|
||||
* @note Static class - no instantiation required
|
||||
* @warning Process termination can cause system instability
|
||||
*/
|
||||
// ProcessManager: static utilities for protection-aware process operations
|
||||
class ProcessManager
|
||||
{
|
||||
public:
|
||||
ProcessManager() = delete; ///< Constructor deleted - static class
|
||||
~ProcessManager() = delete; ///< Destructor deleted - static class
|
||||
ProcessManager() = delete; // Static class - no instances
|
||||
~ProcessManager() = delete;
|
||||
|
||||
/**
|
||||
* @brief Handle 'kill' command from command line
|
||||
* @param argc Argument count from command line
|
||||
* @param argv Argument vector from command line
|
||||
* @param controller Controller instance for protection operations
|
||||
*
|
||||
* Parses command line and terminates specified processes with
|
||||
* automatic protection level matching. Supports both single and
|
||||
* multiple target specification.
|
||||
*
|
||||
* Command format:
|
||||
* - kill <PID|name> -> Single target
|
||||
* - kill <PID1,PID2,name3> -> Multiple targets (comma-separated)
|
||||
*
|
||||
* Features:
|
||||
* - Automatic protection elevation to match target
|
||||
* - Partial name matching (e.g., "note" matches "notepad.exe")
|
||||
* - Case-insensitive matching
|
||||
* - Batch operation with progress reporting
|
||||
*
|
||||
* @note Integrates with Controller for protection manipulation
|
||||
* @warning Terminating system processes can cause system instability
|
||||
*/
|
||||
// Handle 'kill' command: parse args and terminate targets with protection matching
|
||||
static void HandleKillCommand(int argc, wchar_t* argv[], Controller* controller) noexcept;
|
||||
|
||||
private:
|
||||
// === Command Parsing and Validation ===
|
||||
|
||||
/**
|
||||
* @brief Parse comma-separated list of PIDs
|
||||
* @param pidList Comma-separated PID string
|
||||
* @param pids Output vector of parsed PIDs
|
||||
* @return true if parsing successful
|
||||
* @note Handles whitespace and validates numeric values
|
||||
* @note Skips invalid entries and continues parsing
|
||||
*/
|
||||
// Parse comma-separated PID list into vector (skips invalid entries)
|
||||
static bool ParseProcessIds(std::wstring_view pidList, std::vector<DWORD>& pids) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Print kill command usage information
|
||||
*
|
||||
* Displays command syntax, examples, and available options
|
||||
* for the kill command.
|
||||
*/
|
||||
// Print usage information for kill command
|
||||
static void PrintKillUsage() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Terminate process with automatic protection elevation
|
||||
* @param processId Target process ID
|
||||
* @param controller Controller instance for protection operations
|
||||
* @return true if termination successful
|
||||
*
|
||||
* Automatically matches target's protection level before termination
|
||||
* to ensure successful process termination. This is necessary because
|
||||
* protected processes can only be terminated by processes with equal
|
||||
* or higher protection levels.
|
||||
*
|
||||
* @note Uses Controller::SelfProtect for protection elevation
|
||||
* @note Falls back to standard termination if protection matching fails
|
||||
*/
|
||||
// Terminate process by PID, attempting protection elevation via Controller
|
||||
static bool TerminateProcessWithProtection(DWORD processId, Controller* controller) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Check if input string is a numeric PID
|
||||
* @param input String to validate
|
||||
* @return true if string contains only digits
|
||||
* @note Used to distinguish between PID and process name targets
|
||||
*/
|
||||
// Return true if input is numeric PID string
|
||||
static bool IsNumericPid(std::wstring_view input) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Find all process IDs matching name pattern
|
||||
* @param processName Process name or partial name
|
||||
* @return Vector of matching PIDs
|
||||
*
|
||||
* Performs case-insensitive partial matching against running processes.
|
||||
* Example: "note" matches "notepad.exe", "Notepad.exe", "notes.exe"
|
||||
*
|
||||
* @note Uses Toolhelp32 snapshot for process enumeration
|
||||
* @note Returns empty vector if no matches found
|
||||
*/
|
||||
// Find all PIDs whose process name matches the given (partial, case-insensitive)
|
||||
static std::vector<DWORD> FindProcessIdsByName(const std::wstring& processName) noexcept;
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,14 +1,4 @@
|
||||
/**
|
||||
* @file ReportExporter.h
|
||||
* @brief Professional report generation for DPAPI password extraction results
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Exports extraction results in multiple formats (HTML, TXT) with automatic
|
||||
* statistics calculation and modern styling.
|
||||
* Provides comprehensive reporting for credential extraction operations.
|
||||
*/
|
||||
// ReportExporter.h - Export DPAPI extraction results in HTML, TXT, and console formats
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -16,375 +6,75 @@
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
||||
// Forward declarations
|
||||
struct PasswordResult;
|
||||
struct RegistryMasterKey;
|
||||
|
||||
/**
|
||||
* @struct ReportData
|
||||
* @brief Report data aggregation with automatic statistics
|
||||
*
|
||||
* Aggregates all extraction results and calculates statistics automatically
|
||||
* upon construction. Provides convenient access to categorized data.
|
||||
* Used as input for report generation in multiple formats.
|
||||
* Aggregates extraction results and calculates statistics
|
||||
*/
|
||||
struct ReportData
|
||||
{
|
||||
std::vector<PasswordResult> passwordResults; ///< All password extraction results
|
||||
std::vector<RegistryMasterKey> masterKeys; ///< Registry master keys extracted
|
||||
std::wstring outputPath; ///< Output directory path for reports
|
||||
std::string timestamp; ///< Generation timestamp
|
||||
|
||||
/**
|
||||
* @struct Stats
|
||||
* @brief Automatically calculated extraction statistics
|
||||
*
|
||||
* Contains counts and metrics for different credential types
|
||||
* extracted during DPAPI operations.
|
||||
*/
|
||||
std::vector<PasswordResult> passwordResults; ///< Extracted passwords
|
||||
std::vector<RegistryMasterKey> masterKeys; ///< Extracted registry keys
|
||||
std::wstring outputPath; ///< Output directory
|
||||
std::string timestamp; ///< Generation timestamp
|
||||
|
||||
struct Stats {
|
||||
int totalPasswords = 0; ///< Total passwords extracted
|
||||
int chromePasswords = 0; ///< Chrome browser passwords
|
||||
int edgePasswords = 0; ///< Edge browser passwords
|
||||
int wifiPasswords = 0; ///< WiFi credentials
|
||||
int masterKeyCount = 0; ///< Master keys extracted
|
||||
int totalPasswords = 0;
|
||||
int chromePasswords = 0;
|
||||
int edgePasswords = 0;
|
||||
int wifiPasswords = 0;
|
||||
int masterKeyCount = 0;
|
||||
} stats;
|
||||
|
||||
/**
|
||||
* @brief Default constructor
|
||||
*
|
||||
* Creates empty report data structure. Statistics will be
|
||||
* zero-initialized.
|
||||
*/
|
||||
|
||||
ReportData() = default;
|
||||
|
||||
/**
|
||||
* @brief Construct report data with automatic statistics calculation
|
||||
* @param results Password extraction results
|
||||
* @param keys Registry master keys
|
||||
* @param path Output directory path
|
||||
*
|
||||
* Initializes report data with extraction results and automatically
|
||||
* calculates statistics by calling CalculateStatistics().
|
||||
*/
|
||||
ReportData(const std::vector<PasswordResult>& results,
|
||||
ReportData(const std::vector<PasswordResult>& results,
|
||||
const std::vector<RegistryMasterKey>& keys,
|
||||
const std::wstring& path);
|
||||
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief Calculate statistics from results
|
||||
*
|
||||
* Analyzes password results and master keys to populate
|
||||
* statistics structure. Called automatically by constructor.
|
||||
*
|
||||
* @note Private method called automatically on construction
|
||||
*/
|
||||
void CalculateStatistics();
|
||||
void CalculateStatistics(); ///< Populate stats from results
|
||||
};
|
||||
|
||||
/**
|
||||
* @class ReportExporter
|
||||
* @brief Professional report export in multiple formats
|
||||
*
|
||||
* Features:
|
||||
* - HTML export with modern CSS styling and responsive design
|
||||
* - TXT export for lightweight text-based reports
|
||||
* - Automatic statistics calculation and display
|
||||
* - Color-coded categorization (Chrome, Edge, WiFi)
|
||||
* - UTF-8 encoding support
|
||||
* - Professional formatting and layout
|
||||
*
|
||||
* Report Types:
|
||||
* - HTML: Interactive web-based report with styling
|
||||
* - TXT: Plain text report for quick viewing
|
||||
* - Console: Summary display with color coding
|
||||
*
|
||||
* @note Creates timestamped reports in specified output directory
|
||||
* ReportExporter
|
||||
* Generates professional reports in multiple formats
|
||||
*/
|
||||
class ReportExporter
|
||||
{
|
||||
public:
|
||||
ReportExporter() = default; ///< Default constructor
|
||||
~ReportExporter() = default; ///< Default destructor
|
||||
|
||||
// Disable copy semantics
|
||||
ReportExporter(const ReportExporter&) = delete; ///< Copy constructor deleted
|
||||
ReportExporter& operator=(const ReportExporter&) = delete; ///< Copy assignment deleted
|
||||
|
||||
// Enable move semantics
|
||||
ReportExporter(ReportExporter&&) noexcept = default; ///< Move constructor
|
||||
ReportExporter& operator=(ReportExporter&&) noexcept = default; ///< Move assignment
|
||||
ReportExporter() = default;
|
||||
~ReportExporter() = default;
|
||||
|
||||
/**
|
||||
* @brief Export reports in all supported formats
|
||||
* @param data Report data with extraction results
|
||||
* @return true if all formats exported successfully
|
||||
*
|
||||
* Creates both HTML and TXT reports in the output directory.
|
||||
* Also displays summary statistics to console.
|
||||
*
|
||||
* Files created:
|
||||
* - dpapi_results.html: HTML report with full styling
|
||||
* - dpapi_results.txt: Plain text report
|
||||
*
|
||||
* @note Comprehensive reporting across all formats
|
||||
*/
|
||||
bool ExportAllFormats(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Export HTML report with modern styling
|
||||
* @param data Report data with extraction results
|
||||
* @return true if HTML export successful
|
||||
*
|
||||
* Generates professional HTML report with:
|
||||
* - Responsive CSS styling
|
||||
* - Color-coded sections
|
||||
* - Interactive elements
|
||||
* - Statistics dashboard
|
||||
* - Master keys table
|
||||
* - Passwords table (collapsible)
|
||||
* - WiFi credentials section
|
||||
*
|
||||
* @note Creates dpapi_results.html in output directory
|
||||
*/
|
||||
bool ExportHTML(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Export plain text report
|
||||
* @param data Report data with extraction results
|
||||
* @return true if TXT export successful
|
||||
*
|
||||
* Generates lightweight text report with:
|
||||
* - Simple column-based formatting
|
||||
* - Basic statistics
|
||||
* - Master keys listing
|
||||
* - Passwords in readable format
|
||||
* - WiFi credentials section
|
||||
*
|
||||
* @note Creates dpapi_results.txt in output directory
|
||||
*/
|
||||
bool ExportTXT(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Display summary statistics to console
|
||||
* @param data Report data with extraction results
|
||||
*
|
||||
* Prints color-coded summary to console with:
|
||||
* - Total extraction statistics
|
||||
* - File paths for generated reports
|
||||
* - Success/failure indicators
|
||||
* - Quick overview of results
|
||||
*
|
||||
* @note Useful for immediate feedback after extraction
|
||||
*/
|
||||
void DisplaySummary(const ReportData& data) noexcept;
|
||||
ReportExporter(const ReportExporter&) = delete;
|
||||
ReportExporter& operator=(const ReportExporter&) = delete;
|
||||
ReportExporter(ReportExporter&&) noexcept = default;
|
||||
ReportExporter& operator=(ReportExporter&&) noexcept = default;
|
||||
|
||||
bool ExportAllFormats(const ReportData& data) noexcept; ///< HTML + TXT + console summary
|
||||
bool ExportHTML(const ReportData& data) noexcept; ///< Generate HTML report
|
||||
bool ExportTXT(const ReportData& data) noexcept; ///< Generate TXT report
|
||||
void DisplaySummary(const ReportData& data) noexcept; ///< Print console summary
|
||||
|
||||
private:
|
||||
// === HTML Generation Methods ===
|
||||
|
||||
/**
|
||||
* @brief Generate complete HTML content
|
||||
* @param data Report data for generation
|
||||
* @return std::string HTML content as string
|
||||
*
|
||||
* Builds complete HTML document by combining:
|
||||
* - HTML header with CSS styling
|
||||
* - Summary section with statistics
|
||||
* - Master keys table
|
||||
* - Passwords table
|
||||
* - WiFi credentials table
|
||||
*
|
||||
* @note Internal HTML generation implementation
|
||||
*/
|
||||
// HTML generation
|
||||
std::string GenerateHTMLContent(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build HTML header section
|
||||
* @param data Report data for header
|
||||
* @return std::string HTML header content
|
||||
*
|
||||
* Creates HTML head section with:
|
||||
* - Page title and metadata
|
||||
* - CSS styles for responsive design
|
||||
* - JavaScript for interactivity
|
||||
* - Character encoding
|
||||
*
|
||||
* @note Includes modern CSS framework for styling
|
||||
*/
|
||||
std::string BuildHTMLHeader(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build summary section with statistics
|
||||
* @param data Report data for statistics
|
||||
* @return std::string HTML summary section
|
||||
*
|
||||
* Creates statistics dashboard with:
|
||||
* - Total passwords count
|
||||
* - Browser-specific counts
|
||||
* - WiFi credentials count
|
||||
* - Master keys count
|
||||
* - Visual progress bars
|
||||
*
|
||||
* @note Color-coded statistics display
|
||||
*/
|
||||
std::string BuildSummarySection(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build master keys table
|
||||
* @param data Report data with master keys
|
||||
* @return std::string HTML table content
|
||||
*
|
||||
* Creates table displaying:
|
||||
* - Registry key names
|
||||
* - Key data (hex encoded)
|
||||
* - Decryption status
|
||||
* - Data sizes
|
||||
*
|
||||
* @note Technical details for master keys
|
||||
*/
|
||||
std::string BuildMasterKeysTable(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build passwords table
|
||||
* @param data Report data with passwords
|
||||
* @return std::string HTML table content
|
||||
*
|
||||
* Creates interactive table displaying:
|
||||
* - Browser type and profile
|
||||
* - URLs and usernames
|
||||
* - Decrypted passwords
|
||||
* - Extraction status
|
||||
* - Source files
|
||||
*
|
||||
* @note Collapsible sections for large datasets
|
||||
*/
|
||||
std::string BuildPasswordsTable(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build WiFi credentials table
|
||||
* @param data Report data with WiFi credentials
|
||||
* @return std::string HTML table content
|
||||
*
|
||||
* Creates table displaying:
|
||||
* - WiFi profile names
|
||||
* - Network SSIDs
|
||||
* - Security keys
|
||||
* - Connection status
|
||||
*
|
||||
* @note Separate section for wireless credentials
|
||||
*/
|
||||
std::string BuildWiFiTable(const ReportData& data) noexcept;
|
||||
|
||||
// === TXT Generation Methods ===
|
||||
|
||||
/**
|
||||
* @brief Generate complete TXT content
|
||||
* @param data Report data for generation
|
||||
* @return std::wstring TXT content as wide string
|
||||
*
|
||||
* Builds plain text report with:
|
||||
* - Header with timestamp
|
||||
* - Statistics summary
|
||||
* - Master keys listing
|
||||
* - Passwords in columns
|
||||
* - WiFi credentials
|
||||
*
|
||||
* @note Internal TXT generation implementation
|
||||
*/
|
||||
|
||||
// TXT generation
|
||||
std::wstring GenerateTXTContent(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build TXT header section
|
||||
* @param data Report data for header
|
||||
* @return std::wstring TXT header content
|
||||
*
|
||||
* Creates text header with:
|
||||
* - Report title
|
||||
* - Generation timestamp
|
||||
* - Separation lines
|
||||
* - Basic information
|
||||
*
|
||||
* @note Simple formatting for text output
|
||||
*/
|
||||
std::wstring BuildTXTHeader(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build TXT master keys section
|
||||
* @param data Report data with master keys
|
||||
* @return std::wstring TXT master keys content
|
||||
*
|
||||
* Lists master keys in text format:
|
||||
* - Key names and paths
|
||||
* - Hex-encoded data (truncated)
|
||||
* - Decryption status
|
||||
* - Size information
|
||||
*
|
||||
* @note Technical details in readable format
|
||||
*/
|
||||
std::wstring BuildTXTMasterKeys(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build TXT passwords section
|
||||
* @param data Report data with passwords
|
||||
* @return std::wstring TXT passwords content
|
||||
*
|
||||
* Displays passwords in column format:
|
||||
* - Browser and profile
|
||||
* - URL and username
|
||||
* - Password (plaintext)
|
||||
* - Status indicator
|
||||
*
|
||||
* @note Aligned columns for readability
|
||||
*/
|
||||
std::wstring BuildTXTPasswords(const ReportData& data) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Build TXT WiFi credentials section
|
||||
* @param data Report data with WiFi credentials
|
||||
* @return std::wstring TXT WiFi content
|
||||
*
|
||||
* Lists WiFi credentials:
|
||||
* - Profile names
|
||||
* - Network information
|
||||
* - Security keys
|
||||
* - Connection details
|
||||
*
|
||||
* @note Separate section for wireless networks
|
||||
*/
|
||||
std::wstring BuildTXTWiFi(const ReportData& data) noexcept;
|
||||
|
||||
// === Utility Functions ===
|
||||
|
||||
/**
|
||||
* @brief Get HTML report file path
|
||||
* @param outputPath Base output directory
|
||||
* @return std::wstring Full HTML file path
|
||||
*
|
||||
* Constructs complete path for HTML report file.
|
||||
* Format: {outputPath}\dpapi_results.html
|
||||
*/
|
||||
|
||||
// Utilities
|
||||
std::wstring GetHTMLPath(const std::wstring& outputPath) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get TXT report file path
|
||||
* @param outputPath Base output directory
|
||||
* @return std::wstring Full TXT file path
|
||||
*
|
||||
* Constructs complete path for TXT report file.
|
||||
* Format: {outputPath}\dpapi_results.txt
|
||||
*/
|
||||
std::wstring GetTXTPath(const std::wstring& outputPath) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Ensure output directory exists
|
||||
* @param path Directory path to validate
|
||||
* @return bool true if directory exists or was created
|
||||
*
|
||||
* Validates that output directory exists and is writable.
|
||||
* Creates directory structure if missing.
|
||||
*
|
||||
* @note Essential for successful report generation
|
||||
*/
|
||||
bool EnsureOutputDirectory(const std::wstring& path) noexcept;
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,14 +1,4 @@
|
||||
/**
|
||||
* @file ServiceManager.h
|
||||
* @brief NT Service management for single-binary deployment
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Provides Windows Service integration for KVC framework, enabling
|
||||
* background operation and automatic startup.
|
||||
* Supports single-binary operation (same executable runs as service or console).
|
||||
*/
|
||||
// ServiceManager.h - Windows NT service controller for single-binary KVC deployment
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -16,203 +6,64 @@
|
||||
#include <string>
|
||||
#include <memory>
|
||||
|
||||
/**
|
||||
* @class ServiceManager
|
||||
* @brief NT Service management for single-binary deployment
|
||||
*
|
||||
* Features:
|
||||
* - Service installation with automatic start type
|
||||
* - Service lifecycle management (start/stop/uninstall)
|
||||
* - Single-binary operation (same executable runs as service or console)
|
||||
* - Background worker thread for service operations
|
||||
* - Automatic cleanup on service stop
|
||||
*
|
||||
* Service Details:
|
||||
* - Name: KernelVulnerabilityControl
|
||||
* - Display: Kernel Vulnerability Capabilities Framework
|
||||
* - Type: Win32OwnProcess
|
||||
* - Start: Automatic (optional)
|
||||
*
|
||||
* @note Requires administrative privileges for service operations
|
||||
* @warning Service operations affect system configuration
|
||||
*/
|
||||
// Manages Windows service installation, start/stop, and single-binary execution mode
|
||||
class ServiceManager
|
||||
{
|
||||
public:
|
||||
ServiceManager() = default; ///< Default constructor
|
||||
~ServiceManager() = default; ///< Default destructor
|
||||
ServiceManager() = default;
|
||||
~ServiceManager() = default;
|
||||
|
||||
// Disable copy semantics
|
||||
ServiceManager(const ServiceManager&) = delete; ///< Copy constructor deleted
|
||||
ServiceManager& operator=(const ServiceManager&) = delete; ///< Copy assignment deleted
|
||||
ServiceManager(const ServiceManager&) = delete;
|
||||
ServiceManager& operator=(const ServiceManager&) = delete;
|
||||
|
||||
// === Service Lifecycle Management ===
|
||||
|
||||
/**
|
||||
* @brief Install service with automatic start
|
||||
* @param exePath Path to executable (empty = current executable)
|
||||
* @return true if installation successful
|
||||
*
|
||||
* Creates Windows service with the following configuration:
|
||||
* - Service name: KernelVulnerabilityControl
|
||||
* - Display name: Kernel Vulnerability Capabilities Framework
|
||||
* - Description: Provides kernel-level process protection and vulnerability assessment capabilities
|
||||
* - Start type: SERVICE_AUTO_START (automatic startup)
|
||||
* - Service type: SERVICE_WIN32_OWN_PROCESS
|
||||
*
|
||||
* @note Requires administrative privileges
|
||||
* @note Uses current executable path if exePath is empty
|
||||
* @note Adds --service parameter for service mode detection
|
||||
*/
|
||||
|
||||
// Install service (auto-start, Win32OwnProcess, admin required)
|
||||
static bool InstallService(const std::wstring& exePath = L"") noexcept;
|
||||
|
||||
/**
|
||||
* @brief Uninstall service from system
|
||||
* @return true if uninstallation successful
|
||||
*
|
||||
* Stops service if running before uninstall. Removes service
|
||||
* from Service Control Manager database.
|
||||
*
|
||||
* @note Requires administrative privileges
|
||||
* @note Stops service gracefully before removal
|
||||
* @note Returns true if service was not installed
|
||||
*/
|
||||
|
||||
// Uninstall service (stops and removes if exists)
|
||||
static bool UninstallService() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Start service process
|
||||
* @return true if service started successfully
|
||||
*
|
||||
* Starts the installed service via Service Control Manager.
|
||||
* Waits for service to enter running state.
|
||||
*
|
||||
* @note Returns true if service is already running
|
||||
* @note Uses StartServiceW with 30 second timeout
|
||||
*/
|
||||
|
||||
// Start installed service (waits until running)
|
||||
static bool StartServiceProcess() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Stop service process
|
||||
* @return true if service stopped successfully
|
||||
*
|
||||
* Stops the running service via Service Control Manager.
|
||||
* Waits for service to enter stopped state.
|
||||
*
|
||||
* @note Returns true if service is already stopped
|
||||
* @note Uses ControlService with SERVICE_CONTROL_STOP
|
||||
*/
|
||||
|
||||
// Stop running service (graceful shutdown)
|
||||
static bool StopServiceProcess() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Run as Windows Service (service entry point)
|
||||
* @return Exit code (0 = success)
|
||||
*
|
||||
* Main service entry point called when started as service.
|
||||
* Registers service control handler and starts worker thread.
|
||||
*
|
||||
* Service workflow:
|
||||
* 1. Register ServiceMain with SCM
|
||||
* 2. Set service status to SERVICE_RUNNING
|
||||
* 3. Start worker thread for background operations
|
||||
* 4. Wait for stop signal from SCM
|
||||
* 5. Perform graceful shutdown
|
||||
*
|
||||
* @note Called automatically when started as service
|
||||
* @note Registers service control handler for stop/shutdown events
|
||||
*/
|
||||
|
||||
// Run current executable as registered Windows service
|
||||
static int RunAsService() noexcept;
|
||||
|
||||
// === Service Configuration ===
|
||||
|
||||
static constexpr const wchar_t* SERVICE_NAME = L"KernelVulnerabilityControl"; ///< Service internal name
|
||||
static constexpr const wchar_t* SERVICE_DISPLAY_NAME = L"Kernel Vulnerability Capabilities Framework"; ///< Service display name
|
||||
static constexpr const wchar_t* SERVICE_DESCRIPTION = L"Provides kernel-level process protection and vulnerability assessment capabilities"; ///< Service description
|
||||
// === Configuration Constants ===
|
||||
|
||||
static constexpr const wchar_t* SERVICE_NAME = L"KernelVulnerabilityControl";
|
||||
static constexpr const wchar_t* SERVICE_DISPLAY_NAME = L"Kernel Vulnerability Capabilities Framework";
|
||||
static constexpr const wchar_t* SERVICE_DESCRIPTION = L"Provides kernel-level process protection and vulnerability assessment capabilities";
|
||||
|
||||
private:
|
||||
// === Service Entry Points ===
|
||||
|
||||
/**
|
||||
* @brief Service main entry point (SCM callback)
|
||||
* @param argc Argument count from SCM
|
||||
* @param argv Argument vector from SCM
|
||||
*
|
||||
* Called by Service Control Manager when service is started.
|
||||
* Initializes service state and reports status to SCM.
|
||||
*
|
||||
* @note Static callback function for SCM
|
||||
* @note Must call SetServiceStatus to report state changes
|
||||
*/
|
||||
|
||||
// SCM entry callback (initializes and runs service)
|
||||
static VOID WINAPI ServiceMain(DWORD argc, LPWSTR* argv);
|
||||
|
||||
/**
|
||||
* @brief Service control handler (SCM callback)
|
||||
* @param ctrlCode Control code from SCM
|
||||
*
|
||||
* Handles control requests from Service Control Manager:
|
||||
* - SERVICE_CONTROL_STOP: Graceful shutdown
|
||||
* - SERVICE_CONTROL_SHUTDOWN: System shutdown
|
||||
* - SERVICE_CONTROL_INTERROGATE: Status query
|
||||
*
|
||||
* @note Static callback function for SCM
|
||||
* @note Sets stop event for SERVICE_CONTROL_STOP and SERVICE_CONTROL_SHUTDOWN
|
||||
*/
|
||||
|
||||
// SCM control handler (handles stop/shutdown/interrogate)
|
||||
static VOID WINAPI ServiceCtrlHandler(DWORD ctrlCode);
|
||||
|
||||
/**
|
||||
* @brief Service worker thread
|
||||
* @param param Thread parameter (unused)
|
||||
* @return Thread exit code
|
||||
*
|
||||
* Runs service logic in background. Monitors stop event
|
||||
* for graceful shutdown. Performs main service operations.
|
||||
*
|
||||
* @note Runs in separate thread from service main
|
||||
* @note Monitors s_serviceStopEvent for shutdown signals
|
||||
*/
|
||||
|
||||
// Service worker thread (runs background logic)
|
||||
static DWORD WINAPI ServiceWorkerThread(LPVOID param);
|
||||
|
||||
// === Service State Management ===
|
||||
|
||||
static SERVICE_STATUS_HANDLE s_serviceStatusHandle; ///< SCM status handle for service
|
||||
static SERVICE_STATUS s_serviceStatus; ///< Current service status structure
|
||||
static HANDLE s_serviceStopEvent; ///< Stop event handle for graceful shutdown
|
||||
static volatile bool s_serviceRunning; ///< Service running flag
|
||||
// === Internal State ===
|
||||
|
||||
/**
|
||||
* @brief Update service status in SCM
|
||||
* @param currentState New service state
|
||||
* @param exitCode Exit code (default: NO_ERROR)
|
||||
* @param waitHint Wait hint in milliseconds (default: 0)
|
||||
* @return true if status updated successfully
|
||||
*
|
||||
* Reports current service state to Service Control Manager.
|
||||
* Used to inform SCM about service state changes.
|
||||
*
|
||||
* @note Must be called for all service state transitions
|
||||
* @note Sets SERVICE_STATUS structure and calls SetServiceStatus
|
||||
*/
|
||||
static SERVICE_STATUS_HANDLE s_serviceStatusHandle;
|
||||
static SERVICE_STATUS s_serviceStatus;
|
||||
static HANDLE s_serviceStopEvent;
|
||||
static volatile bool s_serviceRunning;
|
||||
|
||||
// Update service status in SCM
|
||||
static bool SetServiceStatus(DWORD currentState, DWORD exitCode = NO_ERROR, DWORD waitHint = 0) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Cleanup service resources
|
||||
*
|
||||
* Performs graceful cleanup when service is stopping:
|
||||
* - Closes stop event handle
|
||||
* - Reports stopped state to SCM
|
||||
* - Cleans up any allocated resources
|
||||
*
|
||||
* @note Called on service stop and shutdown
|
||||
*/
|
||||
|
||||
// Cleanup service resources and report stopped state
|
||||
static void ServiceCleanup() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Initialize service components
|
||||
* @return true if initialization successful
|
||||
*
|
||||
* Initializes service-specific components and resources.
|
||||
* Called at service start before entering running state.
|
||||
*
|
||||
* @note Called from ServiceMain after SCM registration
|
||||
*/
|
||||
|
||||
// Initialize internal service components before running
|
||||
static bool InitializeServiceComponents() noexcept;
|
||||
};
|
||||
};
|
||||
|
||||
@@ -1,15 +1,4 @@
|
||||
/**
|
||||
* @file SessionManager.h
|
||||
* @brief Process protection state management across boot sessions
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Tracks protection state changes and enables restoration after system reboots,
|
||||
* maintaining up to 16 boot sessions with automatic cleanup.
|
||||
* Uses registry-based persistence for cross-boot state tracking.
|
||||
*/
|
||||
|
||||
// SessionManager.h - Manages process protection state across boot sessions via registry persistence
|
||||
#pragma once
|
||||
|
||||
#include "common.h"
|
||||
@@ -21,295 +10,104 @@
|
||||
struct ProcessEntry;
|
||||
class Controller;
|
||||
|
||||
/**
|
||||
* @struct SessionEntry
|
||||
* @brief Single process protection state entry for restoration
|
||||
*
|
||||
* Stores complete protection state of a process at the time of unprotect
|
||||
* operation, enabling precise restoration after system reboot.
|
||||
*/
|
||||
// Single process protection state entry for restoration
|
||||
struct SessionEntry
|
||||
{
|
||||
DWORD Pid; ///< Process ID at time of unprotect operation
|
||||
std::wstring ProcessName; ///< Process executable name for identification
|
||||
UCHAR OriginalProtection; ///< Combined protection level + signer before unprotect
|
||||
UCHAR SignatureLevel; ///< Executable signature level before unprotect
|
||||
UCHAR SectionSignatureLevel; ///< DLL section signature level before unprotect
|
||||
std::wstring Status; ///< Current status: "UNPROTECTED" or "RESTORED"
|
||||
DWORD Pid; // Process ID at unprotect time
|
||||
std::wstring ProcessName; // Executable name
|
||||
UCHAR OriginalProtection; // Original protection level
|
||||
UCHAR SignatureLevel; // Executable signature level
|
||||
UCHAR SectionSignatureLevel; // DLL section signature level
|
||||
std::wstring Status; // "UNPROTECTED" or "RESTORED"
|
||||
};
|
||||
|
||||
/**
|
||||
* @class SessionManager
|
||||
* @brief Manages process protection state across boot sessions
|
||||
*
|
||||
* Features:
|
||||
* - Automatic boot session detection via boot ID + tick count
|
||||
* - Registry-based state persistence in HKLM
|
||||
* - Maximum 16 session history with automatic cleanup
|
||||
* - Restoration by signer type or all processes
|
||||
* - Stale session cleanup on reboot detection
|
||||
* - Status tracking (UNPROTECTED/RESTORED)
|
||||
*
|
||||
* Registry Structure:
|
||||
* HKLM\SOFTWARE\KVC\Sessions\{BootID}_{TickCount}\{SignerName}\{Index}
|
||||
*
|
||||
* @note Uses boot ID from registry and tick count for unique session identification
|
||||
* @warning Requires administrative privileges for HKLM registry access
|
||||
*/
|
||||
// Manages protection state tracking and restoration across reboots (max 16 sessions)
|
||||
class SessionManager
|
||||
{
|
||||
public:
|
||||
/**
|
||||
* @brief Construct session manager
|
||||
*
|
||||
* Initializes internal state but does not automatically detect reboot.
|
||||
* Call DetectAndHandleReboot() manually for reboot detection.
|
||||
*/
|
||||
// Construct session manager (no automatic reboot detection)
|
||||
SessionManager() = default;
|
||||
|
||||
/**
|
||||
* @brief Destructor
|
||||
*
|
||||
* No special cleanup needed - registry operations are atomic.
|
||||
*/
|
||||
// Default destructor (no cleanup needed)
|
||||
~SessionManager() = default;
|
||||
|
||||
// === Session Lifecycle Management ===
|
||||
|
||||
/**
|
||||
* @brief Remove sessions that no longer exist (old boot IDs)
|
||||
*
|
||||
* Scans registry for session entries and removes those from previous
|
||||
* boot sessions. Called automatically on initialization.
|
||||
*
|
||||
* @note Called automatically by DetectAndHandleReboot()
|
||||
*/
|
||||
// Remove outdated session entries from registry
|
||||
void CleanupStaleSessions() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Delete all sessions except current boot session
|
||||
*
|
||||
* Manual cleanup method for removing historical session data.
|
||||
* Useful when session limit is reached or for privacy reasons.
|
||||
*
|
||||
* @note Used for manual cleanup via 'cleanup-sessions' command
|
||||
*/
|
||||
// Delete all sessions except current boot session
|
||||
void CleanupAllSessionsExceptCurrent() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Detect system reboot and cleanup old sessions
|
||||
*
|
||||
* Compares current boot ID with registry-stored value to detect
|
||||
* system reboot. Automatically cleans up stale sessions on reboot.
|
||||
*
|
||||
* @note Should be called at application startup
|
||||
*/
|
||||
// Detect reboot by comparing boot ID and cleanup old sessions
|
||||
void DetectAndHandleReboot() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Enforce maximum session limit (default: 16)
|
||||
* @param maxSessions Maximum number of sessions to keep
|
||||
*
|
||||
* Deletes oldest sessions when limit exceeded. Sessions are sorted
|
||||
* by creation time (boot ID + tick count).
|
||||
*
|
||||
* @note Called automatically when saving new sessions
|
||||
*/
|
||||
// Enforce maximum number of stored sessions (default 16)
|
||||
void EnforceSessionLimit(int maxSessions) noexcept;
|
||||
|
||||
// === State Tracking Operations ===
|
||||
|
||||
/**
|
||||
* @brief Save unprotect operation for future restoration
|
||||
* @param signerName Signer type name (e.g., "Antimalware", "WinTcb")
|
||||
* @param affectedProcesses Vector of processes that were unprotected
|
||||
* @return true if state saved to registry successfully
|
||||
*
|
||||
* Creates new session entry with current boot ID and saves complete
|
||||
* protection state of all affected processes for later restoration.
|
||||
*
|
||||
* @note Each signer type gets separate registry key for organization
|
||||
*/
|
||||
// Save unprotect state for given signer group to registry
|
||||
bool SaveUnprotectOperation(const std::wstring& signerName,
|
||||
const std::vector<ProcessEntry>& affectedProcesses) noexcept;
|
||||
|
||||
// === Restoration Operations ===
|
||||
|
||||
/**
|
||||
* @brief Restore protection for specific signer group
|
||||
* @param signerName Signer type to restore (e.g., "Antimalware")
|
||||
* @param controller Controller instance for protection operations
|
||||
* @return true if restoration successful for all processes
|
||||
*
|
||||
* Loads session entries for specified signer and restores original
|
||||
* protection levels. Only processes with "UNPROTECTED" status are
|
||||
* processed. Updates status to "RESTORED" after successful restoration.
|
||||
*
|
||||
* @note Uses Controller for actual protection manipulation
|
||||
*/
|
||||
// Restore protection for all entries under specified signer
|
||||
bool RestoreBySigner(const std::wstring& signerName, Controller* controller) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Restore all saved protection states
|
||||
* @param controller Controller instance for protection operations
|
||||
* @return true if all restorations successful
|
||||
*
|
||||
* Iterates through all signers in current session and restores
|
||||
* protection for all "UNPROTECTED" processes.
|
||||
*
|
||||
* @note Comprehensive restoration across all signer types
|
||||
*/
|
||||
// Restore all saved protections across all signer groups
|
||||
bool RestoreAll(Controller* controller) noexcept;
|
||||
|
||||
// === Query Operations ===
|
||||
|
||||
/**
|
||||
* @brief Display session history with statistics
|
||||
*
|
||||
* Shows all stored sessions with process counts, timestamps, and
|
||||
* restoration status. Highlights current boot session.
|
||||
*
|
||||
* @note Useful for debugging and session management
|
||||
*/
|
||||
// Display session history and statistics
|
||||
void ShowHistory() noexcept;
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief Get current boot session identifier
|
||||
* @return Session ID string: "{BootID}_{TickCount}"
|
||||
*
|
||||
* Combines boot ID from registry with current tick count for
|
||||
* unique session identification across reboots.
|
||||
*
|
||||
* @note Cached for performance during same execution
|
||||
*/
|
||||
// Get current boot session ID: "{BootID}_{TickCount}"
|
||||
std::wstring GetCurrentBootSession() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Calculate boot time from tick count
|
||||
* @return Formatted boot time string
|
||||
*
|
||||
* Converts system tick count to human-readable boot time
|
||||
* for display in session history.
|
||||
*/
|
||||
// Convert tick count to human-readable boot time
|
||||
std::wstring CalculateBootTime() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get last boot ID from registry
|
||||
* @return Boot ID from last session, or 0 if not found
|
||||
*
|
||||
* Reads stored boot ID from registry to detect system reboots.
|
||||
*/
|
||||
// Read last boot ID from registry
|
||||
ULONGLONG GetLastBootIdFromRegistry() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Save current boot ID to registry
|
||||
* @param bootId Boot ID to save
|
||||
*
|
||||
* Stores current boot ID in registry for reboot detection
|
||||
* in subsequent executions.
|
||||
*/
|
||||
// Save current boot ID to registry
|
||||
void SaveLastBootId(ULONGLONG bootId) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get last tick count from registry
|
||||
* @return Tick count from last session
|
||||
*
|
||||
* Reads stored tick count for session continuity tracking.
|
||||
*/
|
||||
// Read last tick count from registry
|
||||
ULONGLONG GetLastTickCountFromRegistry() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Save current tick count to registry
|
||||
* @param tickCount Tick count to save
|
||||
*
|
||||
* Stores current tick count for precise session identification.
|
||||
*/
|
||||
// Save current tick count to registry
|
||||
void SaveLastTickCount(ULONGLONG tickCount) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get base registry path for sessions
|
||||
* @return "SOFTWARE\\KVC\\Sessions"
|
||||
*
|
||||
* Base registry path where all session data is stored.
|
||||
*/
|
||||
// Return base registry path for sessions
|
||||
std::wstring GetRegistryBasePath() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get registry path for specific session
|
||||
* @param sessionId Session identifier
|
||||
* @return Full registry path to session
|
||||
*
|
||||
* Constructs complete registry path for a specific session.
|
||||
*/
|
||||
// Build full registry path for given session ID
|
||||
std::wstring GetSessionPath(const std::wstring& sessionId) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Load session entries for specific signer
|
||||
* @param signerName Signer type name
|
||||
* @return Vector of session entries
|
||||
*
|
||||
* Reads all session entries for a specific signer from registry.
|
||||
*/
|
||||
// Load all session entries for given signer
|
||||
std::vector<SessionEntry> LoadSessionEntries(const std::wstring& signerName) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Load session entries from specific registry path
|
||||
* @param sessionPath Registry path to session
|
||||
* @param signerName Signer type name
|
||||
* @return Vector of session entries
|
||||
*
|
||||
* Internal method for reading session entries from arbitrary paths.
|
||||
*/
|
||||
// Load session entries from given registry path
|
||||
std::vector<SessionEntry> LoadSessionEntriesFromPath(const std::wstring& sessionPath,
|
||||
const std::wstring& signerName) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Write session entry to registry
|
||||
* @param signerName Signer type name
|
||||
* @param index Entry index within signer group
|
||||
* @param entry Session entry data to write
|
||||
* @return true if write successful
|
||||
*
|
||||
* Stores individual session entry in registry with proper value types.
|
||||
*/
|
||||
// Write single session entry to registry
|
||||
bool WriteSessionEntry(const std::wstring& signerName, DWORD index, const SessionEntry& entry) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Update entry status in registry
|
||||
* @param signerName Signer type name
|
||||
* @param index Entry index to update
|
||||
* @param newStatus New status string ("UNPROTECTED" or "RESTORED")
|
||||
* @return true if update successful
|
||||
*
|
||||
* Updates status field of existing session entry after restoration.
|
||||
*/
|
||||
// Update status ("UNPROTECTED"/"RESTORED") for specific entry
|
||||
bool UpdateEntryStatus(const std::wstring& signerName, DWORD index, const std::wstring& newStatus) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Get all session IDs from registry
|
||||
* @return Vector of session ID strings
|
||||
*
|
||||
* Enumerates all existing session IDs in registry for cleanup operations.
|
||||
*/
|
||||
// Enumerate all stored session IDs in registry
|
||||
std::vector<std::wstring> GetAllSessionIds() noexcept;
|
||||
|
||||
/**
|
||||
* @brief Open or create registry key
|
||||
* @param path Registry path
|
||||
* @return Registry key handle or nullptr on failure
|
||||
*
|
||||
* Helper method for registry operations that creates keys if missing.
|
||||
*/
|
||||
// Open or create registry key by path
|
||||
HKEY OpenOrCreateKey(const std::wstring& path) noexcept;
|
||||
|
||||
/**
|
||||
* @brief Recursively delete registry key and all subkeys
|
||||
* @param hKeyParent Parent key handle
|
||||
* @param subKey Subkey name to delete
|
||||
* @return true if deletion successful
|
||||
*
|
||||
* Comprehensive registry key deletion for session cleanup.
|
||||
*/
|
||||
// Recursively delete registry key and all its subkeys
|
||||
bool DeleteKeyRecursive(HKEY hKeyParent, const std::wstring& subKey) noexcept;
|
||||
};
|
||||
};
|
||||
|
||||
361
kvc/common.h
361
kvc/common.h
@@ -1,13 +1,5 @@
|
||||
/**
|
||||
* @file common.h
|
||||
* @brief Common definitions, utilities and includes for KVC Framework
|
||||
* @author Marek Wesolowski
|
||||
* @date 2025
|
||||
* @copyright KVC Framework
|
||||
*
|
||||
* Central header containing Windows API includes, type definitions,
|
||||
* logging system, and cross-cutting utilities used throughout the framework.
|
||||
*/
|
||||
// common.h
|
||||
// Common definitions, utilities and includes for KVC Framework
|
||||
|
||||
#pragma once
|
||||
|
||||
@@ -34,40 +26,34 @@
|
||||
#pragma comment(lib, "crypt32.lib")
|
||||
|
||||
// Session management constants
|
||||
inline constexpr int MAX_SESSIONS = 16; ///< Maximum number of stored sessions
|
||||
inline constexpr int MAX_SESSIONS = 16;
|
||||
|
||||
#ifdef BUILD_DATE
|
||||
#define __DATE__ BUILD_DATE ///< Build date override for reproducible builds
|
||||
#define __DATE__ BUILD_DATE
|
||||
#endif
|
||||
|
||||
#ifdef BUILD_TIME
|
||||
#define __TIME__ BUILD_TIME ///< Build time override for reproducible builds
|
||||
#define __TIME__ BUILD_TIME
|
||||
#endif
|
||||
|
||||
#define kvc_DEBUG_ENABLED 0 ///< Global debug flag (0=disabled, 1=enabled)
|
||||
#define kvc_DEBUG_ENABLED 0
|
||||
|
||||
#ifdef ERROR
|
||||
#undef ERROR ///< Undefine Windows ERROR macro to avoid conflicts
|
||||
#undef ERROR
|
||||
#endif
|
||||
|
||||
#ifndef SHTDN_REASON_MAJOR_SOFTWARE
|
||||
#define SHTDN_REASON_MAJOR_SOFTWARE 0x00030000 ///< Software shutdown reason
|
||||
#define SHTDN_REASON_MAJOR_SOFTWARE 0x00030000
|
||||
#endif
|
||||
|
||||
#ifndef SHTDN_REASON_MINOR_RECONFIGURE
|
||||
#define SHTDN_REASON_MINOR_RECONFIGURE 0x00000004 ///< Reconfiguration shutdown reason
|
||||
#define SHTDN_REASON_MINOR_RECONFIGURE 0x00000004
|
||||
#endif
|
||||
|
||||
// Smart module handle management
|
||||
|
||||
/**
|
||||
* @brief Custom deleter for HMODULE with FreeLibrary
|
||||
*/
|
||||
// Custom deleter for HMODULE with FreeLibrary
|
||||
struct ModuleDeleter {
|
||||
/**
|
||||
* @brief Free library module
|
||||
* @param mod Module handle to free
|
||||
*/
|
||||
void operator()(HMODULE mod) const noexcept {
|
||||
if (mod) {
|
||||
FreeLibrary(mod);
|
||||
@@ -75,31 +61,19 @@ struct ModuleDeleter {
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Custom deleter for system modules (no cleanup needed)
|
||||
*/
|
||||
// Custom deleter for system modules (no cleanup needed)
|
||||
struct SystemModuleDeleter {
|
||||
/**
|
||||
* @brief No-op deleter for system modules from GetModuleHandle
|
||||
* @param mod Module handle (ignored)
|
||||
*/
|
||||
void operator()(HMODULE) const noexcept {
|
||||
// System modules obtained via GetModuleHandle don't need to be freed
|
||||
}
|
||||
};
|
||||
|
||||
using ModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, ModuleDeleter>; ///< Smart pointer for loaded modules
|
||||
using SystemModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, SystemModuleDeleter>; ///< Smart pointer for system modules
|
||||
using ModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, ModuleDeleter>;
|
||||
using SystemModuleHandle = std::unique_ptr<std::remove_pointer_t<HMODULE>, SystemModuleDeleter>;
|
||||
|
||||
// Fixed logging system with proper buffer size and variadic handling
|
||||
|
||||
/**
|
||||
* @brief Print formatted message with prefix
|
||||
* @tparam Args Variadic template arguments
|
||||
* @param prefix Message prefix (e.g., "[DEBUG] ")
|
||||
* @param format Format string (printf-style)
|
||||
* @param args Format arguments
|
||||
*/
|
||||
// Print formatted message with prefix
|
||||
template<typename... Args>
|
||||
void PrintMessage(const wchar_t* prefix, const wchar_t* format, Args&&... args)
|
||||
{
|
||||
@@ -121,12 +95,7 @@ void PrintMessage(const wchar_t* prefix, const wchar_t* format, Args&&... args)
|
||||
std::wcout << ss.str();
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Print critical message in red color
|
||||
* @tparam Args Variadic template arguments
|
||||
* @param format Format string (printf-style)
|
||||
* @param args Format arguments
|
||||
*/
|
||||
// Print critical message in red color
|
||||
template<typename... Args>
|
||||
void PrintCriticalMessage(const wchar_t* format, Args&&... args) {
|
||||
HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE);
|
||||
@@ -154,20 +123,17 @@ void PrintCriticalMessage(const wchar_t* format, Args&&... args) {
|
||||
}
|
||||
|
||||
#if kvc_DEBUG_ENABLED
|
||||
#define DEBUG(format, ...) PrintMessage(L"[DEBUG] ", format, ##__VA_ARGS__) ///< Debug logging macro
|
||||
#define DEBUG(format, ...) PrintMessage(L"[DEBUG] ", format, ##__VA_ARGS__)
|
||||
#else
|
||||
#define DEBUG(format, ...) do {} while(0) ///< Debug logging macro (disabled)
|
||||
#define DEBUG(format, ...) do {} while(0)
|
||||
#endif
|
||||
|
||||
#define ERROR(format, ...) PrintMessage(L"[-] ", format, ##__VA_ARGS__) ///< Error logging macro
|
||||
#define INFO(format, ...) PrintMessage(L"[*] ", format, ##__VA_ARGS__) ///< Info logging macro
|
||||
#define SUCCESS(format, ...) PrintMessage(L"[+] ", format, ##__VA_ARGS__) ///< Success logging macro
|
||||
#define CRITICAL(format, ...) PrintCriticalMessage(format, ##__VA_ARGS__) ///< Critical error logging macro
|
||||
#define ERROR(format, ...) PrintMessage(L"[-] ", format, ##__VA_ARGS__)
|
||||
#define INFO(format, ...) PrintMessage(L"[*] ", format, ##__VA_ARGS__)
|
||||
#define SUCCESS(format, ...) PrintMessage(L"[+] ", format, ##__VA_ARGS__)
|
||||
#define CRITICAL(format, ...) PrintCriticalMessage(format, ##__VA_ARGS__)
|
||||
|
||||
/**
|
||||
* @brief Log last error for failed function
|
||||
* @param f Function name that failed
|
||||
*/
|
||||
// Log last error for failed function
|
||||
#define LASTERROR(f) \
|
||||
do { \
|
||||
wchar_t buf[256]; \
|
||||
@@ -177,138 +143,121 @@ void PrintCriticalMessage(const wchar_t* format, Args&&... args) {
|
||||
|
||||
// Windows protection type definitions
|
||||
|
||||
/**
|
||||
* @brief Process protection level enumeration
|
||||
*/
|
||||
// Process protection level enumeration
|
||||
enum class PS_PROTECTED_TYPE : UCHAR
|
||||
{
|
||||
None = 0, ///< No protection
|
||||
ProtectedLight = 1, ///< Protected Process Light (PPL)
|
||||
Protected = 2 ///< Protected Process (PP)
|
||||
None = 0,
|
||||
ProtectedLight = 1,
|
||||
Protected = 2
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Process signer type enumeration
|
||||
*/
|
||||
// Process signer type enumeration
|
||||
enum class PS_PROTECTED_SIGNER : UCHAR
|
||||
{
|
||||
None = 0, ///< No signer
|
||||
Authenticode = 1, ///< Authenticode signed
|
||||
CodeGen = 2, ///< Code generation
|
||||
Antimalware = 3, ///< Antimalware products
|
||||
Lsa = 4, ///< Local Security Authority
|
||||
Windows = 5, ///< Windows signed
|
||||
WinTcb = 6, ///< Windows TCB (Trusted Computing Base)
|
||||
WinSystem = 7, ///< Windows system components
|
||||
App = 8, ///< Application signer
|
||||
Max = 9 ///< Maximum value
|
||||
None = 0,
|
||||
Authenticode = 1,
|
||||
CodeGen = 2,
|
||||
Antimalware = 3,
|
||||
Lsa = 4,
|
||||
Windows = 5,
|
||||
WinTcb = 6,
|
||||
WinSystem = 7,
|
||||
App = 8,
|
||||
Max = 9
|
||||
};
|
||||
|
||||
// Service-related constants
|
||||
|
||||
/**
|
||||
* @brief Service-related constants and configuration
|
||||
*/
|
||||
namespace ServiceConstants {
|
||||
inline constexpr wchar_t SERVICE_NAME[] = L"KernelVulnerabilityControl"; ///< Service internal name
|
||||
inline constexpr wchar_t SERVICE_DISPLAY_NAME[] = L"Kernel Vulnerability Capabilities Framework"; ///< Service display name
|
||||
inline constexpr wchar_t SERVICE_PARAM[] = L"--service"; ///< Service mode parameter
|
||||
inline constexpr wchar_t SERVICE_NAME[] = L"KernelVulnerabilityControl";
|
||||
inline constexpr wchar_t SERVICE_DISPLAY_NAME[] = L"Kernel Vulnerability Capabilities Framework";
|
||||
inline constexpr wchar_t SERVICE_PARAM[] = L"--service";
|
||||
|
||||
// Keyboard hook settings
|
||||
inline constexpr int CTRL_SEQUENCE_LENGTH = 5; ///< Number of Ctrl presses for activation
|
||||
inline constexpr DWORD CTRL_SEQUENCE_TIMEOUT_MS = 2000; ///< Sequence timeout in milliseconds
|
||||
inline constexpr DWORD CTRL_DEBOUNCE_MS = 50; ///< Key debounce period
|
||||
inline constexpr int CTRL_SEQUENCE_LENGTH = 5;
|
||||
inline constexpr DWORD CTRL_SEQUENCE_TIMEOUT_MS = 2000;
|
||||
inline constexpr DWORD CTRL_DEBOUNCE_MS = 50;
|
||||
}
|
||||
|
||||
// DPAPI constants for password extraction
|
||||
|
||||
/**
|
||||
* @brief DPAPI-related constants for password extraction operations
|
||||
*/
|
||||
namespace DPAPIConstants {
|
||||
inline constexpr int SQLITE_OK = 0; ///< SQLite success code
|
||||
inline constexpr int SQLITE_ROW = 100; ///< SQLite row available code
|
||||
inline constexpr int SQLITE_DONE = 101; ///< SQLite operation complete code
|
||||
inline constexpr int SQLITE_OPEN_READONLY = 0x00000001; ///< SQLite read-only mode
|
||||
inline constexpr int SQLITE_OK = 0;
|
||||
inline constexpr int SQLITE_ROW = 100;
|
||||
inline constexpr int SQLITE_DONE = 101;
|
||||
inline constexpr int SQLITE_OPEN_READONLY = 0x00000001;
|
||||
|
||||
inline std::string GetChromeV10Prefix() { return "v10"; } ///< Chrome encrypted key prefix
|
||||
inline std::string GetChromeDPAPIPrefix() { return "DPAPI"; } ///< Chrome DPAPI prefix
|
||||
inline std::string GetChromeV10Prefix() { return "v10"; }
|
||||
inline std::string GetChromeDPAPIPrefix() { return "DPAPI"; }
|
||||
|
||||
inline std::wstring GetSecurityPolicySecrets() { return L"SECURITY\\Policy\\Secrets"; } ///< Registry path for LSA secrets
|
||||
inline std::wstring GetDPAPISystemKey() { return L"DPAPI_SYSTEM"; } ///< DPAPI system key name
|
||||
inline std::wstring GetNLKMKey() { return L"NL$KM"; } ///< NL$KM key name
|
||||
inline std::wstring GetDefaultPasswordKey() { return L"DefaultPassword"; } ///< Default password key name
|
||||
inline std::wstring GetSecurityPolicySecrets() { return L"SECURITY\\Policy\\Secrets"; }
|
||||
inline std::wstring GetDPAPISystemKey() { return L"DPAPI_SYSTEM"; }
|
||||
inline std::wstring GetNLKMKey() { return L"NL$KM"; }
|
||||
inline std::wstring GetDefaultPasswordKey() { return L"DefaultPassword"; }
|
||||
|
||||
inline std::wstring GetCurrVal() { return L"CurrVal"; } ///< Current value registry key
|
||||
inline std::wstring GetOldVal() { return L"OldVal"; } ///< Old value registry key
|
||||
inline std::wstring GetCurrVal() { return L"CurrVal"; }
|
||||
inline std::wstring GetOldVal() { return L"OldVal"; }
|
||||
|
||||
inline std::wstring GetChromeUserData() { return L"\\Google\\Chrome\\User Data"; } ///< Chrome user data path
|
||||
inline std::wstring GetEdgeUserData() { return L"\\Microsoft\\Edge\\User Data"; } ///< Edge user data path
|
||||
inline std::wstring GetLocalStateFile() { return L"\\Local State"; } ///< Local state filename
|
||||
inline std::wstring GetLoginDataFile() { return L"\\Login Data"; } ///< Login data filename
|
||||
inline std::wstring GetChromeUserData() { return L"\\Google\\Chrome\\User Data"; }
|
||||
inline std::wstring GetEdgeUserData() { return L"\\Microsoft\\Edge\\User Data"; }
|
||||
inline std::wstring GetLocalStateFile() { return L"\\Local State"; }
|
||||
inline std::wstring GetLoginDataFile() { return L"\\Login Data"; }
|
||||
|
||||
inline std::string GetEncryptedKeyField() { return "\"encrypted_key\":"; } ///< JSON field for encrypted key
|
||||
inline std::string GetEncryptedKeyField() { return "\"encrypted_key\":"; }
|
||||
|
||||
inline std::string GetLocalAppData() { return "LOCALAPPDATA"; } ///< Local app data environment variable
|
||||
inline std::string GetLocalAppData() { return "LOCALAPPDATA"; }
|
||||
|
||||
inline std::wstring GetHTMLExt() { return L".html"; } ///< HTML file extension
|
||||
inline std::wstring GetTXTExt() { return L".txt"; } ///< Text file extension
|
||||
inline std::wstring GetDBExt() { return L".db"; } ///< Database file extension
|
||||
inline std::wstring GetHTMLExt() { return L".html"; }
|
||||
inline std::wstring GetTXTExt() { return L".txt"; }
|
||||
inline std::wstring GetDBExt() { return L".db"; }
|
||||
|
||||
inline std::wstring GetTempLoginDB() { return L"temp_login_data.db"; } ///< Temporary login database name
|
||||
inline std::wstring GetTempPattern() { return L"temp_login_data"; } ///< Temporary file pattern
|
||||
inline std::wstring GetTempLoginDB() { return L"temp_login_data.db"; }
|
||||
inline std::wstring GetTempPattern() { return L"temp_login_data"; }
|
||||
|
||||
inline std::string GetNetshShowProfiles() { return "netsh wlan show profiles"; } ///< Netsh show profiles command
|
||||
inline std::string GetNetshShowProfileKey() { return "netsh wlan show profile name=\""; } ///< Netsh show profile command
|
||||
inline std::string GetNetshKeyClear() { return "\" key=clear"; } ///< Netsh key clear parameter
|
||||
inline std::string GetNetshShowProfiles() { return "netsh wlan show profiles"; }
|
||||
inline std::string GetNetshShowProfileKey() { return "netsh wlan show profile name=\""; }
|
||||
inline std::string GetNetshKeyClear() { return "\" key=clear"; }
|
||||
|
||||
inline std::string GetWiFiProfileMarker() { return "All User Profile"; } ///< WiFi profile marker in output
|
||||
inline std::string GetWiFiKeyContent() { return "Key Content"; } ///< WiFi key content marker
|
||||
inline std::string GetWiFiProfileMarker() { return "All User Profile"; }
|
||||
inline std::string GetWiFiKeyContent() { return "Key Content"; }
|
||||
|
||||
inline std::string GetLoginQuery() { return "SELECT origin_url, username_value, password_value FROM logins"; } ///< SQL query for login data
|
||||
inline std::string GetLoginQuery() { return "SELECT origin_url, username_value, password_value FROM logins"; }
|
||||
|
||||
inline std::wstring GetStatusDecrypted() { return L"DECRYPTED"; } ///< Decryption successful status
|
||||
inline std::wstring GetStatusClearText() { return L"CLEAR_TEXT"; } ///< Clear text status
|
||||
inline std::wstring GetStatusEncrypted() { return L"ENCRYPTED"; } ///< Encrypted status
|
||||
inline std::wstring GetStatusFailed() { return L"FAILED"; } ///< Operation failed status
|
||||
inline std::wstring GetStatusExtracted() { return L"EXTRACTED"; } ///< Data extracted status
|
||||
inline std::wstring GetStatusDecrypted() { return L"DECRYPTED"; }
|
||||
inline std::wstring GetStatusClearText() { return L"CLEAR_TEXT"; }
|
||||
inline std::wstring GetStatusEncrypted() { return L"ENCRYPTED"; }
|
||||
inline std::wstring GetStatusFailed() { return L"FAILED"; }
|
||||
inline std::wstring GetStatusExtracted() { return L"EXTRACTED"; }
|
||||
}
|
||||
|
||||
// Dynamic API loading globals for driver operations
|
||||
extern ModuleHandle g_advapi32; ///< advapi32.dll module handle
|
||||
extern SystemModuleHandle g_kernel32; ///< kernel32.dll module handle
|
||||
extern decltype(&CreateServiceW) g_pCreateServiceW; ///< CreateServiceW function pointer
|
||||
extern decltype(&OpenServiceW) g_pOpenServiceW; ///< OpenServiceW function pointer
|
||||
extern decltype(&StartServiceW) g_pStartServiceW; ///< StartServiceW function pointer
|
||||
extern decltype(&DeleteService) g_pDeleteService; ///< DeleteService function pointer
|
||||
extern decltype(&CreateFileW) g_pCreateFileW; ///< CreateFileW function pointer
|
||||
extern decltype(&ControlService) g_pControlService; ///< ControlService function pointer
|
||||
extern ModuleHandle g_advapi32;
|
||||
extern SystemModuleHandle g_kernel32;
|
||||
extern decltype(&CreateServiceW) g_pCreateServiceW;
|
||||
extern decltype(&OpenServiceW) g_pOpenServiceW;
|
||||
extern decltype(&StartServiceW) g_pStartServiceW;
|
||||
extern decltype(&DeleteService) g_pDeleteService;
|
||||
extern decltype(&CreateFileW) g_pCreateFileW;
|
||||
extern decltype(&ControlService) g_pControlService;
|
||||
|
||||
// Service mode detection
|
||||
extern bool g_serviceMode; ///< Service mode flag
|
||||
extern volatile bool g_interrupted; ///< Interruption flag for graceful shutdown
|
||||
extern bool g_serviceMode;
|
||||
extern volatile bool g_interrupted;
|
||||
|
||||
// Core driver functions
|
||||
bool InitDynamicAPIs() noexcept; ///< Initialize dynamic API pointers
|
||||
extern "C" const wchar_t* GetServiceNameRaw(); ///< Get service name (ASM function)
|
||||
std::wstring GetServiceName() noexcept; ///< Get service name (C++ wrapper)
|
||||
std::wstring GetDriverFileName() noexcept; ///< Get driver filename
|
||||
void GenerateFakeActivity() noexcept; ///< Generate fake activity for stealth
|
||||
std::wstring GetSystemTempPath() noexcept; ///< Get system temp path
|
||||
bool InitDynamicAPIs() noexcept;
|
||||
extern "C" const wchar_t* GetServiceNameRaw();
|
||||
std::wstring GetServiceName() noexcept;
|
||||
std::wstring GetDriverFileName() noexcept;
|
||||
void GenerateFakeActivity() noexcept;
|
||||
std::wstring GetSystemTempPath() noexcept;
|
||||
|
||||
// Service utility functions
|
||||
bool IsServiceInstalled() noexcept; ///< Check if service is installed
|
||||
bool IsServiceRunning() noexcept; ///< Check if service is running
|
||||
std::wstring GetCurrentExecutablePath() noexcept; ///< Get current executable path
|
||||
bool IsServiceInstalled() noexcept;
|
||||
bool IsServiceRunning() noexcept;
|
||||
std::wstring GetCurrentExecutablePath() noexcept;
|
||||
|
||||
// Driver path helper with dynamic discovery and fallback mechanism
|
||||
|
||||
/**
|
||||
* @brief Get DriverStore path for driver operations
|
||||
* @return DriverStore path string
|
||||
* @note Searches for actual avc.inf_amd64_* directory in DriverStore FileRepository
|
||||
* @note Creates directory if needed, falls back to system32\drivers on failure
|
||||
*/
|
||||
// Get DriverStore path for driver operations
|
||||
// Searches for actual avc.inf_amd64_* directory in DriverStore FileRepository
|
||||
// Creates directory if needed, falls back to system32\drivers on failure
|
||||
inline std::wstring GetDriverStorePath() noexcept {
|
||||
wchar_t windowsDir[MAX_PATH];
|
||||
if (GetWindowsDirectoryW(windowsDir, MAX_PATH) == 0) {
|
||||
@@ -339,11 +288,8 @@ inline std::wstring GetDriverStorePath() noexcept {
|
||||
return targetPath;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get DriverStore path with directory creation
|
||||
* @return DriverStore path string, empty on critical failure
|
||||
* @note Enhanced version that ensures directory exists before returning path
|
||||
*/
|
||||
// Get DriverStore path with directory creation
|
||||
// Enhanced version that ensures directory exists before returning path
|
||||
inline std::wstring GetDriverStorePathSafe() noexcept {
|
||||
std::wstring driverPath = GetDriverStorePath();
|
||||
|
||||
@@ -353,34 +299,28 @@ inline std::wstring GetDriverStorePathSafe() noexcept {
|
||||
// Try to create if it doesn't exist
|
||||
if (!CreateDirectoryW(driverPath.c_str(), nullptr) &&
|
||||
GetLastError() != ERROR_ALREADY_EXISTS) {
|
||||
return L""; // Critical failure
|
||||
return L"";
|
||||
}
|
||||
} else if (!(attrs & FILE_ATTRIBUTE_DIRECTORY)) {
|
||||
return L""; // Path exists but is not a directory
|
||||
return L"";
|
||||
}
|
||||
|
||||
return driverPath;
|
||||
}
|
||||
|
||||
// KVC combined binary processing constants
|
||||
inline constexpr std::array<BYTE, 7> KVC_XOR_KEY = { 0xA0, 0xE2, 0x80, 0x8B, 0xE2, 0x80, 0x8C }; ///< XOR key for binary decryption
|
||||
inline constexpr wchar_t KVC_DATA_FILE[] = L"kvc.dat"; ///< Combined binary data file
|
||||
inline constexpr wchar_t KVC_PASS_FILE[] = L"kvc_pass.exe"; ///< Password extractor executable
|
||||
inline constexpr wchar_t KVC_CRYPT_FILE[] = L"kvc_crypt.dll"; ///< Cryptography DLL
|
||||
inline constexpr std::array<BYTE, 7> KVC_XOR_KEY = { 0xA0, 0xE2, 0x80, 0x8B, 0xE2, 0x80, 0x8C };
|
||||
inline constexpr wchar_t KVC_DATA_FILE[] = L"kvc.dat";
|
||||
inline constexpr wchar_t KVC_PASS_FILE[] = L"kvc_pass.exe";
|
||||
inline constexpr wchar_t KVC_CRYPT_FILE[] = L"kvc_crypt.dll";
|
||||
|
||||
// ============================================================================
|
||||
// CONSOLIDATED UTILITY NAMESPACES
|
||||
// ============================================================================
|
||||
|
||||
/**
|
||||
* @brief String conversion and manipulation utilities
|
||||
*/
|
||||
// String conversion and manipulation utilities
|
||||
namespace StringUtils {
|
||||
/**
|
||||
* @brief Convert UTF-8 string to wide string (UTF-16 LE)
|
||||
* @param str UTF-8 encoded string
|
||||
* @return UTF-16 LE encoded wide string, empty on failure
|
||||
*/
|
||||
// Convert UTF-8 string to wide string (UTF-16 LE)
|
||||
inline std::wstring UTF8ToWide(const std::string& str) noexcept {
|
||||
if (str.empty()) return L"";
|
||||
|
||||
@@ -394,11 +334,7 @@ namespace StringUtils {
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Convert wide string (UTF-16 LE) to UTF-8 string
|
||||
* @param wstr UTF-16 LE encoded wide string
|
||||
* @return UTF-8 encoded string, empty on failure
|
||||
*/
|
||||
// Convert wide string (UTF-16 LE) to UTF-8 string
|
||||
inline std::string WideToUTF8(const std::wstring& wstr) noexcept {
|
||||
if (wstr.empty()) return "";
|
||||
|
||||
@@ -413,21 +349,13 @@ namespace StringUtils {
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Convert string to lowercase in-place
|
||||
* @param str String to convert (modified in-place)
|
||||
* @return Reference to modified string
|
||||
*/
|
||||
// Convert string to lowercase in-place
|
||||
inline std::wstring& ToLowerCase(std::wstring& str) noexcept {
|
||||
std::transform(str.begin(), str.end(), str.begin(), ::towlower);
|
||||
return str;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Create lowercase copy of string
|
||||
* @param str String to convert
|
||||
* @return Lowercase copy of input string
|
||||
*/
|
||||
// Create lowercase copy of string
|
||||
inline std::wstring ToLowerCaseCopy(const std::wstring& str) noexcept {
|
||||
std::wstring result = str;
|
||||
std::transform(result.begin(), result.end(), result.begin(), ::towlower);
|
||||
@@ -435,14 +363,9 @@ namespace StringUtils {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Path and filesystem manipulation utilities
|
||||
*/
|
||||
// Path and filesystem manipulation utilities
|
||||
namespace PathUtils {
|
||||
/**
|
||||
* @brief Get user's Downloads folder path
|
||||
* @return Full path to Downloads folder, empty on failure
|
||||
*/
|
||||
// Get user's Downloads folder path
|
||||
inline std::wstring GetDownloadsPath() noexcept {
|
||||
wchar_t* downloadsPath = nullptr;
|
||||
if (SHGetKnownFolderPath(FOLDERID_Downloads, 0, nullptr, &downloadsPath) != S_OK) {
|
||||
@@ -454,10 +377,8 @@ namespace PathUtils {
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get default secrets output path with timestamp
|
||||
* @return Path in format: Downloads\Secrets_DD.MM.YYYY
|
||||
*/
|
||||
// Get default secrets output path with timestamp
|
||||
// Format: Downloads\Secrets_DD.MM.YYYY
|
||||
inline std::wstring GetDefaultSecretsOutputPath() noexcept {
|
||||
std::wstring downloadsPath = GetDownloadsPath();
|
||||
if (downloadsPath.empty()) {
|
||||
@@ -476,11 +397,7 @@ namespace PathUtils {
|
||||
return downloadsPath + L"\\Secrets" + dateStr;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Ensure directory exists, create if missing
|
||||
* @param path Directory path to validate/create
|
||||
* @return true if directory exists or was created
|
||||
*/
|
||||
// Ensure directory exists, create if missing
|
||||
inline bool EnsureDirectoryExists(const std::wstring& path) noexcept {
|
||||
if (path.empty()) return false;
|
||||
|
||||
@@ -492,11 +409,7 @@ namespace PathUtils {
|
||||
return std::filesystem::create_directories(path, ec) && !ec;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Validate directory write access
|
||||
* @param path Directory path to test
|
||||
* @return true if directory is writable
|
||||
*/
|
||||
// Validate directory write access
|
||||
inline bool ValidateDirectoryWritable(const std::wstring& path) noexcept {
|
||||
try {
|
||||
std::filesystem::create_directories(path);
|
||||
@@ -516,15 +429,10 @@ namespace PathUtils {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Time and date formatting utilities
|
||||
*/
|
||||
// Time and date formatting utilities
|
||||
namespace TimeUtils {
|
||||
/**
|
||||
* @brief Get formatted timestamp string
|
||||
* @param format Format specifier: "date_only", "datetime_file", "datetime_display"
|
||||
* @return Formatted timestamp string
|
||||
*/
|
||||
// Get formatted timestamp string
|
||||
// Formats: "date_only", "datetime_file", "datetime_display"
|
||||
inline std::wstring GetFormattedTimestamp(const char* format = "datetime_file") noexcept {
|
||||
auto now = std::chrono::system_clock::now();
|
||||
auto time = std::chrono::system_clock::to_time_t(now);
|
||||
@@ -547,15 +455,9 @@ namespace TimeUtils {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Cryptographic and encoding utilities
|
||||
*/
|
||||
// Cryptographic and encoding utilities
|
||||
namespace CryptoUtils {
|
||||
/**
|
||||
* @brief Decode Base64 string to binary data
|
||||
* @param encoded Base64-encoded string
|
||||
* @return Decoded binary data, empty on failure
|
||||
*/
|
||||
// Decode Base64 string to binary data
|
||||
inline std::vector<BYTE> Base64Decode(const std::string& encoded) noexcept {
|
||||
if (encoded.empty()) return {};
|
||||
|
||||
@@ -575,12 +477,7 @@ namespace CryptoUtils {
|
||||
return decoded;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Convert byte vector to hexadecimal string
|
||||
* @param bytes Binary data to convert
|
||||
* @param maxBytes Maximum bytes to convert (0 = unlimited)
|
||||
* @return Hex string representation
|
||||
*/
|
||||
// Convert byte vector to hexadecimal string
|
||||
inline std::string BytesToHex(const std::vector<BYTE>& bytes, size_t maxBytes = 0) noexcept {
|
||||
if (bytes.empty()) return "";
|
||||
|
||||
@@ -601,15 +498,9 @@ namespace CryptoUtils {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Windows privilege manipulation utilities
|
||||
*/
|
||||
// Windows privilege manipulation utilities
|
||||
namespace PrivilegeUtils {
|
||||
/**
|
||||
* @brief Enable specified privilege in current process token
|
||||
* @param privilege Privilege name constant
|
||||
* @return true if privilege enabled successfully
|
||||
*/
|
||||
// Enable specified privilege in current process token
|
||||
inline bool EnablePrivilege(LPCWSTR privilege) noexcept {
|
||||
HANDLE hToken;
|
||||
if (!OpenProcessToken(GetCurrentProcess(),
|
||||
|
||||
Reference in New Issue
Block a user