diff --git a/dpmdk/include/CommonModuleAPI.hpp b/dpmdk/include/CommonModuleAPI.hpp index a6ce942..96b4b5b 100644 --- a/dpmdk/include/CommonModuleAPI.hpp +++ b/dpmdk/include/CommonModuleAPI.hpp @@ -33,6 +33,7 @@ #include #include #include +#include "ModuleOperations.hpp" /** * @brief Fatal log level constant @@ -163,59 +164,6 @@ extern "C" { * @return The module path */ const char* dpm_get_module_path(void); - - /** - * @brief Checks if a module exists - * - * Verifies if a module exists at the configured module path. - * - * @param module_name Name of the module to check - * @return true if the module exists, false otherwise - */ - bool dpm_module_exists(const char* module_name); - - /** - * @brief Loads a DPM module - * - * Attempts to load a module from the configured module path. - * - * @param module_name Name of the module to load - * @param module_handle Pointer to store the loaded module handle - * @return 0 on success, non-zero on failure - */ - int dpm_load_module(const char* module_name, void** module_handle); - - /** - * @brief Checks if a symbol exists in a module - * - * Verifies if a specific symbol exists in a loaded module. - * - * @param module_handle Handle to a loaded module - * @param symbol_name Name of the symbol to check - * @return true if the symbol exists, false otherwise - */ - bool dpm_symbol_exists(void* module_handle, const char* symbol_name); - - /** - * @brief Executes a symbol in a module - * - * Attempts to execute a function in a loaded module. - * - * @param module_handle Handle to a loaded module - * @param symbol_name Name of the symbol to execute - * @param args Arguments to pass to the function - * @return 0 on success, non-zero on failure - */ - int dpm_execute_symbol(void* module_handle, const char* symbol_name, void* args); - - /** - * @brief Unloads a module - * - * Frees resources used by a loaded module. - * - * @param module_handle Handle to a loaded module - */ - void dpm_unload_module(void* module_handle); } /** diff --git a/dpmdk/include/ModuleOperations.hpp b/dpmdk/include/ModuleOperations.hpp new file mode 100644 index 0000000..2a7db69 --- /dev/null +++ b/dpmdk/include/ModuleOperations.hpp @@ -0,0 +1,88 @@ +/** + * @file ModuleOperations.hpp + * @brief C++ interface for module operations with direct passthrough + * + * @copyright Copyright (c) 2025 SILO GROUP LLC + * @author Chris Punches + * + * Part of the Dark Horse Linux Package Manager (DPM) + */ + +#pragma once + +#include +#include +#include +#include +#include + +/** + * @brief Checks if a module exists + * + * Verifies if a module exists at the configured module path. + * + * @param module_name Name of the module to check + * @return true if the module exists, false otherwise + */ +bool dpm_module_exists(const char* module_name); + +/** + * @brief Loads a DPM module + * + * Attempts to load a module from the configured module path. + * + * @param module_name Name of the module to load + * @param module_handle Pointer to store the loaded module handle + * @return 0 on success, non-zero on failure + */ +int dpm_load_module(const char* module_name, void** module_handle); + +/** + * @brief Checks if a symbol exists in a module + * + * Verifies if a specific symbol exists in a loaded module. + * + * @param module_handle Handle to a loaded module + * @param symbol_name Name of the symbol to check + * @return true if the symbol exists, false otherwise + */ +bool dpm_symbol_exists(void* module_handle, const char* symbol_name); + +/** + * @brief Executes a symbol in a module with direct argument passthrough + * + * Template function that directly passes any number of arguments to the target function. + * + * @tparam Args Variable argument types to pass to the function + * @param module_handle Handle to a loaded module + * @param symbol_name Name of the symbol to execute + * @param args Arguments to pass to the function + * @return Return value from the executed function + */ +template +int dpm_execute_symbol(void* module_handle, const char* symbol_name, Args&&... args) { + if (!module_handle || !symbol_name) return 1; + + // Clear any previous error + dlerror(); + + // Look up the symbol with the correct function signature + typedef int (*FunctionPtr)(Args...); + FunctionPtr func = reinterpret_cast(dlsym(module_handle, symbol_name)); + + // Check for errors + const char* error = dlerror(); + if (error || !func) return 1; + + // Call the function with the provided arguments - direct passthrough + return func(std::forward(args)...); +} + +/** + * @brief Unloads a module + * + * Frees resources used by a loaded module. + * + * @param module_handle Handle to a loaded module + */ +void dpm_unload_module(void* module_handle); \ No newline at end of file diff --git a/dpmdk/include/StandaloneModuleImpl.hpp b/dpmdk/include/StandaloneModuleImpl.hpp index fec7a10..4c8eb0b 100644 --- a/dpmdk/include/StandaloneModuleImpl.hpp +++ b/dpmdk/include/StandaloneModuleImpl.hpp @@ -99,98 +99,6 @@ inline const char* dpm_get_module_path(void) { return env_path ? env_path : "/usr/lib/dpm/modules/"; } -/** - * @brief Standalone implementation of dpm_module_exists - */ -inline bool dpm_module_exists(const char* module_name) { - if (!module_name) return false; - - // Get the module path - const char* module_path = dpm_get_module_path(); - if (!module_path) return false; - - // Build path to the module - std::string module_file = std::string(module_path) + "/" + module_name + ".so"; - - // Check if file exists - struct stat buffer; - return (stat(module_file.c_str(), &buffer) == 0); -} - -/** - * @brief Standalone implementation of dpm_load_module - */ -inline int dpm_load_module(const char* module_name, void** module_handle) { - if (!module_name || !module_handle) return 1; - - // Get the module path - const char* module_path = dpm_get_module_path(); - if (!module_path) return 1; - - // Build path to the module - std::string module_file = std::string(module_path) + "/" + module_name + ".so"; - - // Check if the file exists - if (!dpm_module_exists(module_name)) return 1; - - // Load the module - *module_handle = dlopen(module_file.c_str(), RTLD_LAZY); - if (!*module_handle) return 1; - - return 0; -} - -/** - * @brief Standalone implementation of dpm_symbol_exists - */ -inline bool dpm_symbol_exists(void* module_handle, const char* symbol_name) { - if (!module_handle || !symbol_name) return false; - - // Clear any error - dlerror(); - - // Look up the symbol - void* symbol = dlsym(module_handle, symbol_name); - - // Check for errors - const char* error = dlerror(); - if (error) return false; - - return (symbol != NULL); -} - -/** - * @brief Standalone implementation of dpm_execute_symbol - */ -inline int dpm_execute_symbol(void* module_handle, const char* symbol_name, void* args) { - if (!module_handle || !symbol_name) return 1; - - // Clear any error - dlerror(); - - // Look up the symbol - void* symbol = dlsym(module_handle, symbol_name); - - // Check for errors - const char* error = dlerror(); - if (error || !symbol) return 1; - - // Cast to function pointer and call - typedef int (*FunctionPtr)(void*); - FunctionPtr func = (FunctionPtr)symbol; - - return func(args); -} - -/** - * @brief Standalone implementation of dpm_unload_module - */ -inline void dpm_unload_module(void* module_handle) { - if (module_handle) { - dlclose(module_handle); - } -} - /** * @brief Standalone module main function * diff --git a/dpmdk/src/CommonModuleAPI.cpp b/dpmdk/src/CommonModuleAPI.cpp index c22724a..b8f8076 100644 --- a/dpmdk/src/CommonModuleAPI.cpp +++ b/dpmdk/src/CommonModuleAPI.cpp @@ -31,81 +31,5 @@ // Only define these functions when not in standalone mode #ifndef BUILD_STANDALONE -extern "C" bool dpm_module_exists(const char* module_name) { - if (!module_name) return false; - - // Get the module path - const char* module_path = dpm_get_module_path(); - if (!module_path) return false; - - // Build path to the module - std::string module_file = std::string(module_path) + "/" + module_name + ".so"; - - // Check if file exists - struct stat buffer; - return (stat(module_file.c_str(), &buffer) == 0); -} - -extern "C" int dpm_load_module(const char* module_name, void** module_handle) { - if (!module_name || !module_handle) return 1; - - // Get the module path - const char* module_path = dpm_get_module_path(); - if (!module_path) return 1; - - // Build path to the module - std::string module_file = std::string(module_path) + "/" + module_name + ".so"; - - // Check if the file exists - if (!dpm_module_exists(module_name)) return 1; - - // Load the module - *module_handle = dlopen(module_file.c_str(), RTLD_LAZY); - if (!*module_handle) return 1; - - return 0; -} - -extern "C" bool dpm_symbol_exists(void* module_handle, const char* symbol_name) { - if (!module_handle || !symbol_name) return false; - - // Clear any error - dlerror(); - - // Look up the symbol - void* symbol = dlsym(module_handle, symbol_name); - - // Check for errors - const char* error = dlerror(); - if (error) return false; - - return (symbol != NULL); -} - -extern "C" int dpm_execute_symbol(void* module_handle, const char* symbol_name, void* args) { - if (!module_handle || !symbol_name) return 1; - - // Clear any error - dlerror(); - - // Look up the symbol - void* symbol = dlsym(module_handle, symbol_name); - - // Check for errors - const char* error = dlerror(); - if (error || !symbol) return 1; - - // Cast to function pointer and call - typedef int (*FunctionPtr)(void*); - FunctionPtr func = (FunctionPtr)symbol; - - return func(args); -} - -extern "C" void dpm_unload_module(void* module_handle) { - if (module_handle) { - dlclose(module_handle); - } -} #endif // BUILD_STANDALONE \ No newline at end of file diff --git a/dpmdk/src/ModuleOperations.cpp b/dpmdk/src/ModuleOperations.cpp new file mode 100644 index 0000000..4760033 --- /dev/null +++ b/dpmdk/src/ModuleOperations.cpp @@ -0,0 +1,69 @@ +/** +* @file ModuleOperations.cpp + * @brief Implementation of C++ interface for module operations + * + * @copyright Copyright (c) 2025 SILO GROUP LLC + * @author Chris Punches + * + * Part of the Dark Horse Linux Package Manager (DPM) + */ + +#include "ModuleOperations.hpp" + + +bool dpm_module_exists(const char* module_name) { + if (!module_name) return false; + + // Get the module path + const char* module_path = dpm_get_module_path(); + if (!module_path) return false; + + // Build path to the module + std::string module_file = std::string(module_path) + "/" + module_name + ".so"; + + // Check if file exists + struct stat buffer; + return (stat(module_file.c_str(), &buffer) == 0); +} + +int dpm_load_module(const char* module_name, void** module_handle) { + if (!module_name || !module_handle) return 1; + + // Get the module path + const char* module_path = dpm_get_module_path(); + if (!module_path) return 1; + + // Build path to the module + std::string module_file = std::string(module_path) + "/" + module_name + ".so"; + + // Check if the file exists + if (!dpm_module_exists(module_name)) return 1; + + // Load the module + *module_handle = dlopen(module_file.c_str(), RTLD_LAZY); + if (!*module_handle) return 1; + + return 0; +} + +bool dpm_symbol_exists(void* module_handle, const char* symbol_name) { + if (!module_handle || !symbol_name) return false; + + // Clear any error + dlerror(); + + // Look up the symbol + void* symbol = dlsym(module_handle, symbol_name); + + // Check for errors + const char* error = dlerror(); + if (error) return false; + + return (symbol != nullptr); +} + +void dpm_unload_module(void* module_handle) { + if (module_handle) { + dlclose(module_handle); + } +} \ No newline at end of file diff --git a/modules/build/src/sealing.cpp b/modules/build/src/sealing.cpp index c2f0cca..af32506 100644 --- a/modules/build/src/sealing.cpp +++ b/modules/build/src/sealing.cpp @@ -1,5 +1,7 @@ #include "sealing.hpp" +// TODO finalize's seal currently assumes unsealed components which is not necessarily the case. +// it should unseal if sealed and seal whole so that the metadata refresh is always accurate bool file_already_compressed(const std::string& path) { diff --git a/modules/verify/CMakeLists.txt b/modules/verify/CMakeLists.txt index 4c1ab3e..7976931 100644 --- a/modules/verify/CMakeLists.txt +++ b/modules/verify/CMakeLists.txt @@ -17,6 +17,8 @@ add_library(verify MODULE ${DPM_ROOT_DIR}/dpmdk/src/CommonModuleAPI.cpp src/cli_parsers.cpp src/verification.cpp + src/checksum.cpp + ../../dpmdk/src/ModuleOperations.cpp ) # Set output properties @@ -43,6 +45,8 @@ add_executable(verify_standalone ${DPM_ROOT_DIR}/dpmdk/src/CommonModuleAPI.cpp src/cli_parsers.cpp src/verification.cpp + src/checksum.cpp + ../../dpmdk/src/ModuleOperations.cpp ) # Define the BUILD_STANDALONE macro for the standalone build diff --git a/modules/verify/include/checksum.hpp b/modules/verify/include/checksum.hpp new file mode 100644 index 0000000..431919f --- /dev/null +++ b/modules/verify/include/checksum.hpp @@ -0,0 +1,51 @@ +/** +* @file checksum.hpp + * @brief Header file for package checksum verification functions + * + * Defines functions for verifying checksums of DPM package components. + * + * @copyright Copyright (c) 2025 SILO GROUP LLC + * @author Chris Punches + * + * Part of the Dark Horse Linux Package Manager (DPM) + */ +#pragma once + +#include +#include +#include +#include "checksum.hpp" + +/** + * @brief Verify the CONTENTS_MANIFEST_DIGEST file + * + * Compares checksums in manifest with actual file checksums + * + * @param stage_dir Path to the stage directory + * @param build_module Handle to the loaded build module + * @return 0 on success, non-zero on failure + */ +int checksum_verify_contents_digest(const std::string& stage_dir, void* build_module); + +/** + * @brief Verify the HOOKS_DIGEST file + * + * Compares checksums in hooks digest with actual file checksums + * + * @param stage_dir Path to the stage directory + * @param build_module Handle to the loaded build module + * @return 0 on success, non-zero on failure + */ +int checksum_verify_hooks_digest(const std::string& stage_dir, void* build_module); + +/** + * @brief Verify the PACKAGE_DIGEST file + * + * Calculates the combined checksum of CONTENTS_MANIFEST_DIGEST and HOOKS_DIGEST + * and compares it with the value in PACKAGE_DIGEST + * + * @param stage_dir Path to the stage directory + * @param build_module Handle to the loaded build module + * @return 0 on success, non-zero on failure + */ +int checksum_verify_package_digest(const std::string& stage_dir, void* build_module); diff --git a/modules/verify/include/verification.hpp b/modules/verify/include/verification.hpp index 5084551..0463b72 100644 --- a/modules/verify/include/verification.hpp +++ b/modules/verify/include/verification.hpp @@ -15,6 +15,8 @@ #include #include #include +#include "commands.hpp" +#include "checksum.hpp" /** * @brief Verifies checksums for a package file diff --git a/modules/verify/src/checksum.cpp b/modules/verify/src/checksum.cpp new file mode 100644 index 0000000..02cf556 --- /dev/null +++ b/modules/verify/src/checksum.cpp @@ -0,0 +1,300 @@ +/** + * @file checksum.cpp + * @brief Implementation of package checksum verification functions + * + * Implements functions for verifying checksums of DPM package components. + * + * @copyright Copyright (c) 2025 SILO GROUP LLC + * @author Chris Punches + * + * Part of the Dark Horse Linux Package Manager (DPM) + */ + +#include "checksum.hpp" +#include +#include +#include + +int checksum_verify_contents_digest(const std::string& stage_dir, void* build_module) { + dpm_log(LOG_INFO, "Verifying contents manifest digest..."); + std::filesystem::path manifest_file = std::filesystem::path(stage_dir) / "metadata" / "CONTENTS_MANIFEST_DIGEST"; + + if (!std::filesystem::exists(manifest_file)) { + dpm_log(LOG_ERROR, "CONTENTS_MANIFEST_DIGEST file not found"); + return 1; + } + + // Get the generate_file_checksum function from the build module + typedef std::string (*FileChecksumFunc)(const std::filesystem::path&); + dlerror(); // Clear any previous error + FileChecksumFunc generate_checksum = (FileChecksumFunc)dlsym(build_module, "generate_file_checksum"); + + const char* dlsym_error = dlerror(); + if (dlsym_error) { + dpm_log(LOG_ERROR, ("Failed to find generate_file_checksum function: " + + std::string(dlsym_error)).c_str()); + return 1; + } + + try { + std::ifstream manifest(manifest_file); + if (!manifest.is_open()) { + dpm_log(LOG_ERROR, ("Failed to open manifest file: " + manifest_file.string()).c_str()); + return 1; + } + + std::string line; + int line_number = 0; + int errors = 0; + + while (std::getline(manifest, line)) { + line_number++; + + // Skip empty lines + if (line.empty()) continue; + + // Parse the line: control_designation checksum permissions owner:group /path/to/file + std::istringstream iss(line); + char control_designation; + std::string checksum, permissions, ownership, file_path; + + if (!(iss >> control_designation >> checksum >> permissions >> ownership)) { + dpm_log(LOG_WARN, ("Malformed manifest line " + std::to_string(line_number) + + ": " + line).c_str()); + continue; + } + + // Get the rest of the line as the file path + std::getline(iss >> std::ws, file_path); + + if (file_path.empty()) { + dpm_log(LOG_WARN, ("Missing file path in manifest line " + + std::to_string(line_number)).c_str()); + continue; + } + + // Remove leading slash if present + if (file_path[0] == '/') { + file_path = file_path.substr(1); + } + + // Build the full path to the file in the contents directory + std::filesystem::path full_file_path = std::filesystem::path(stage_dir) / "contents" / file_path; + + // Check if the file exists + if (!std::filesystem::exists(full_file_path)) { + dpm_log(LOG_ERROR, ("File not found: " + full_file_path.string()).c_str()); + errors++; + continue; + } + + // Calculate the checksum of the file and compare with the manifest + std::string calculated_checksum = generate_checksum(full_file_path); + + if (calculated_checksum.empty()) { + dpm_log(LOG_ERROR, ("Failed to calculate checksum for: " + + full_file_path.string()).c_str()); + errors++; + continue; + } + + if (calculated_checksum != checksum) { + dpm_log(LOG_ERROR, ("Checksum mismatch for " + full_file_path.string() + + "\n Expected: " + checksum + + "\n Actual: " + calculated_checksum).c_str()); + errors++; + } + } + + manifest.close(); + + if (errors > 0) { + dpm_log(LOG_ERROR, (std::to_string(errors) + " checksum errors found in contents manifest").c_str()); + return 1; + } + + dpm_log(LOG_INFO, "Contents manifest checksum verification successful"); + return 0; + + } catch (const std::exception& e) { + dpm_log(LOG_ERROR, ("Error processing contents manifest: " + std::string(e.what())).c_str()); + return 1; + } +} + +int checksum_verify_hooks_digest(const std::string& stage_dir, void* build_module) { + dpm_log(LOG_INFO, "Verifying hooks digest..."); + std::filesystem::path hooks_digest_file = std::filesystem::path(stage_dir) / "metadata" / "HOOKS_DIGEST"; + + if (!std::filesystem::exists(hooks_digest_file)) { + dpm_log(LOG_ERROR, "HOOKS_DIGEST file not found"); + return 1; + } + + // Get the generate_file_checksum function from the build module + typedef std::string (*FileChecksumFunc)(const std::filesystem::path&); + dlerror(); // Clear any previous error + FileChecksumFunc generate_checksum = (FileChecksumFunc)dlsym(build_module, "generate_file_checksum"); + + const char* dlsym_error = dlerror(); + if (dlsym_error) { + dpm_log(LOG_ERROR, ("Failed to find generate_file_checksum function: " + + std::string(dlsym_error)).c_str()); + return 1; + } + + try { + std::ifstream hooks_digest(hooks_digest_file); + if (!hooks_digest.is_open()) { + dpm_log(LOG_ERROR, ("Failed to open hooks digest file: " + + hooks_digest_file.string()).c_str()); + return 1; + } + + std::string line; + int errors = 0; + + while (std::getline(hooks_digest, line)) { + // Skip empty lines + if (line.empty()) continue; + + // Parse the line: checksum filename + std::istringstream iss(line); + std::string checksum, filename; + + if (!(iss >> checksum >> filename)) { + dpm_log(LOG_WARN, ("Malformed hooks digest line: " + line).c_str()); + continue; + } + + // Build the full path to the hook file + std::filesystem::path hook_path = std::filesystem::path(stage_dir) / "hooks" / filename; + + // Check if the file exists + if (!std::filesystem::exists(hook_path)) { + dpm_log(LOG_ERROR, ("Hook file not found: " + hook_path.string()).c_str()); + errors++; + continue; + } + + // Calculate the checksum of the hook file + std::string calculated_checksum = generate_checksum(hook_path); + + if (calculated_checksum.empty()) { + dpm_log(LOG_ERROR, ("Failed to calculate checksum for: " + + hook_path.string()).c_str()); + errors++; + continue; + } + + if (calculated_checksum != checksum) { + dpm_log(LOG_ERROR, ("Checksum mismatch for " + hook_path.string() + + "\n Expected: " + checksum + + "\n Actual: " + calculated_checksum).c_str()); + errors++; + } + } + + hooks_digest.close(); + + if (errors > 0) { + dpm_log(LOG_ERROR, (std::to_string(errors) + " checksum errors found in hooks digest").c_str()); + return 1; + } + + dpm_log(LOG_INFO, "Hooks digest checksum verification successful"); + return 0; + + } catch (const std::exception& e) { + dpm_log(LOG_ERROR, ("Error processing hooks digest: " + std::string(e.what())).c_str()); + return 1; + } +} + +int checksum_verify_package_digest(const std::string& stage_dir, void* build_module) { + dpm_log(LOG_INFO, "Verifying package digest..."); + std::filesystem::path metadata_dir = std::filesystem::path(stage_dir) / "metadata"; + std::filesystem::path package_digest_file = metadata_dir / "PACKAGE_DIGEST"; + std::filesystem::path manifest_file = metadata_dir / "CONTENTS_MANIFEST_DIGEST"; + std::filesystem::path hooks_digest_file = metadata_dir / "HOOKS_DIGEST"; + + if (!std::filesystem::exists(package_digest_file)) { + dpm_log(LOG_ERROR, "PACKAGE_DIGEST file not found"); + return 1; + } + + if (!std::filesystem::exists(manifest_file)) { + dpm_log(LOG_ERROR, "CONTENTS_MANIFEST_DIGEST file not found"); + return 1; + } + + if (!std::filesystem::exists(hooks_digest_file)) { + dpm_log(LOG_ERROR, "HOOKS_DIGEST file not found"); + return 1; + } + + // Get the checksum functions from the build module + typedef std::string (*FileChecksumFunc)(const std::filesystem::path&); + typedef std::string (*StringChecksumFunc)(const std::string&); + + dlerror(); // Clear any previous error + FileChecksumFunc generate_file_checksum = (FileChecksumFunc)dlsym(build_module, "generate_file_checksum"); + const char* dlsym_error = dlerror(); + if (dlsym_error) { + dpm_log(LOG_ERROR, ("Failed to find generate_file_checksum function: " + + std::string(dlsym_error)).c_str()); + return 1; + } + + dlerror(); // Clear any previous error + StringChecksumFunc generate_string_checksum = (StringChecksumFunc)dlsym(build_module, "generate_string_checksum"); + dlsym_error = dlerror(); + if (dlsym_error) { + dpm_log(LOG_ERROR, ("Failed to find generate_string_checksum function: " + + std::string(dlsym_error)).c_str()); + return 1; + } + + // Read the package digest from the file + std::string package_digest; + try { + std::ifstream digest_file(package_digest_file); + if (!digest_file.is_open()) { + dpm_log(LOG_ERROR, ("Failed to open digest file: " + package_digest_file.string()).c_str()); + return 1; + } + std::getline(digest_file, package_digest); + digest_file.close(); + } catch (const std::exception& e) { + dpm_log(LOG_ERROR, ("Error reading package digest: " + std::string(e.what())).c_str()); + return 1; + } + + // Calculate checksums of the digest files + std::string contents_manifest_checksum = generate_file_checksum(manifest_file); + std::string hooks_digest_checksum = generate_file_checksum(hooks_digest_file); + + if (contents_manifest_checksum.empty() || hooks_digest_checksum.empty()) { + dpm_log(LOG_ERROR, "Failed to calculate checksums for digest files"); + return 1; + } + + // Combine checksums and calculate package digest + std::string combined_checksums = contents_manifest_checksum + hooks_digest_checksum; + std::string calculated_package_digest = generate_string_checksum(combined_checksums); + + if (calculated_package_digest.empty()) { + dpm_log(LOG_ERROR, "Failed to calculate package digest"); + return 1; + } + + // Compare with the stored package digest + if (calculated_package_digest != package_digest) { + dpm_log(LOG_ERROR, ("Package digest mismatch\n Expected: " + package_digest + + "\n Actual: " + calculated_package_digest).c_str()); + return 1; + } + + dpm_log(LOG_INFO, "Package digest verification successful"); + return 0; +} \ No newline at end of file diff --git a/modules/verify/src/verification.cpp b/modules/verify/src/verification.cpp index 69cb2ec..df86d37 100644 --- a/modules/verify/src/verification.cpp +++ b/modules/verify/src/verification.cpp @@ -40,10 +40,64 @@ int verify_checksums_stage(const std::string& stage_dir) { return 1; } - // Placeholder implementation dpm_log(LOG_INFO, ("Verifying checksums for stage directory: " + stage_dir).c_str()); - dpm_log(LOG_INFO, "Stage directory checksum verification not yet implemented"); + // First, ensure the components are unsealed (uncompressed) + dpm_log(LOG_INFO, "Ensuring stage components are unsealed..."); + + // Load the build module to access functions + void* build_module = nullptr; + int result = check_and_load_build_module(build_module); + if (result != 0 || build_module == nullptr) { + dpm_log(LOG_ERROR, "Failed to load build module"); + return 1; + } + + // Get the unseal_stage_components function + typedef int (*UnsealComponentsFunc)(const std::filesystem::path&); + dlerror(); // Clear any previous error + UnsealComponentsFunc unseal_components = (UnsealComponentsFunc)dlsym(build_module, "unseal_stage_components"); + const char* dlsym_error = dlerror(); + if (dlsym_error) { + dpm_log(LOG_ERROR, ("Failed to find unseal_stage_components function: " + std::string(dlsym_error)).c_str()); + dlclose(build_module); + return 1; + } + + // Call the function to unseal the components + result = unseal_components(std::filesystem::path(stage_dir)); + if (result != 0) { + dpm_log(LOG_ERROR, "Failed to unseal stage components"); + dlclose(build_module); + return 1; + } + + // Verify checksums + result = checksum_verify_package_digest(stage_dir, build_module); + if (result != 0) { + dpm_log(LOG_ERROR, "Package digest verification failed"); + dlclose(build_module); + return 1; + } + + result = checksum_verify_contents_digest(stage_dir, build_module); + if (result != 0) { + dpm_log(LOG_ERROR, "Contents manifest verification failed"); + dlclose(build_module); + return 1; + } + + result = checksum_verify_hooks_digest(stage_dir, build_module); + if (result != 0) { + dpm_log(LOG_ERROR, "Hooks digest verification failed"); + dlclose(build_module); + return 1; + } + + // Clean up + dlclose(build_module); + + dpm_log(LOG_INFO, "All checksums verified successfully"); return 0; }