From d511080814dc78ad39a63f2071003c07ee37673c Mon Sep 17 00:00:00 2001 From: WerWolv Date: Sat, 13 Jan 2024 00:34:13 +0100 Subject: [PATCH] impr: Make plugin features and subcommands work in statically linked builds --- lib/libimhex/include/hex/plugin.hpp | 64 +++++++++++++++---- lib/libimhex/source/api/plugin_manager.cpp | 2 + .../decompress/source/plugin_decompress.cpp | 14 ++-- 3 files changed, 60 insertions(+), 20 deletions(-) diff --git a/lib/libimhex/include/hex/plugin.hpp b/lib/libimhex/include/hex/plugin.hpp index 879eb404d..d0bc2af57 100644 --- a/lib/libimhex/include/hex/plugin.hpp +++ b/lib/libimhex/include/hex/plugin.hpp @@ -13,6 +13,30 @@ #include #include +namespace { + struct PluginFunctionHelperInstantiation {}; +} + +template +struct PluginFeatureFunctionHelper { + static void* getFeatures(); +}; + +template +struct PluginSubCommandsFunctionHelper { + static void* getSubCommands(); +}; + +template +void* PluginFeatureFunctionHelper::getFeatures() { + return nullptr; +} + +template +void* PluginSubCommandsFunctionHelper::getSubCommands() { + return nullptr; +} + #if defined (IMHEX_STATIC_LINK_PLUGINS) #define IMHEX_PLUGIN_VISIBILITY_PREFIX static #else @@ -60,9 +84,15 @@ ImGui::SetCurrentContext(ctx); \ GImGui = ctx; \ } \ + IMHEX_PLUGIN_VISIBILITY_PREFIX void* getFeatures() { \ + return PluginFeatureFunctionHelper::getFeatures(); \ + } \ + IMHEX_PLUGIN_VISIBILITY_PREFIX void* getSubCommands() { \ + return PluginSubCommandsFunctionHelper::getSubCommands(); \ + } \ IMHEX_PLUGIN_VISIBILITY_PREFIX void initializePlugin(); \ extern "C" [[gnu::visibility("default")]] void WOLV_TOKEN_CONCAT(forceLinkPlugin_, IMHEX_PLUGIN_NAME)() { \ - hex::PluginManager::addPlugin(name, hex::PluginFunctions { \ + hex::PluginManager::addPlugin(name, hex::PluginFunctions { \ initializePlugin, \ nullptr, \ getPluginName, \ @@ -71,8 +101,8 @@ getPluginDescription, \ getCompatibleVersion, \ setImGuiContext, \ - nullptr, \ - nullptr \ + getSubCommands, \ + getFeatures \ }); \ } \ IMHEX_PLUGIN_VISIBILITY_PREFIX void initializePlugin() @@ -87,18 +117,26 @@ */ #define IMHEX_PLUGIN_SUBCOMMANDS() IMHEX_PLUGIN_SUBCOMMANDS_IMPL() -#define IMHEX_PLUGIN_SUBCOMMANDS_IMPL() \ - extern std::vector g_subCommands; \ - extern "C" [[gnu::visibility("default")]] void* getSubCommands() { \ - return &g_subCommands; \ - } \ +#define IMHEX_PLUGIN_SUBCOMMANDS_IMPL() \ + extern std::vector g_subCommands; \ + template<> \ + struct PluginSubCommandsFunctionHelper { \ + static void* getSubCommands(); \ + }; \ + void* PluginSubCommandsFunctionHelper::getSubCommands() { \ + return &g_subCommands; \ + } \ std::vector g_subCommands #define IMHEX_FEATURE_ENABLED(feature) WOLV_TOKEN_CONCAT(WOLV_TOKEN_CONCAT(WOLV_TOKEN_CONCAT(IMHEX_PLUGIN_, IMHEX_PLUGIN_NAME), _FEATURE_), feature) #define IMHEX_PLUGIN_FEATURES() IMHEX_PLUGIN_FEATURES_IMPL() -#define IMHEX_PLUGIN_FEATURES_IMPL() \ - extern std::vector g_features; \ - extern "C" [[gnu::visibility("default")]] void* getFeatures() { \ - return &g_features; \ - } \ +#define IMHEX_PLUGIN_FEATURES_IMPL() \ + extern std::vector g_features; \ + template<> \ + struct PluginFeatureFunctionHelper { \ + static void* getFeatures(); \ + }; \ + void* PluginFeatureFunctionHelper::getFeatures() { \ + return &g_features; \ + } \ std::vector g_features diff --git a/lib/libimhex/source/api/plugin_manager.cpp b/lib/libimhex/source/api/plugin_manager.cpp index f73e60be3..f9ed8636b 100644 --- a/lib/libimhex/source/api/plugin_manager.cpp +++ b/lib/libimhex/source/api/plugin_manager.cpp @@ -196,6 +196,8 @@ namespace hex { std::span Plugin::getFeatures() const { if (m_functions.getFeaturesFunction != nullptr) { const auto result = m_functions.getFeaturesFunction(); + if (result == nullptr) + return { }; return *static_cast*>(result); } else { diff --git a/plugins/decompress/source/plugin_decompress.cpp b/plugins/decompress/source/plugin_decompress.cpp index dc57de028..9f6262800 100644 --- a/plugins/decompress/source/plugin_decompress.cpp +++ b/plugins/decompress/source/plugin_decompress.cpp @@ -14,15 +14,15 @@ namespace hex::plugin::decompress { using namespace hex; using namespace hex::plugin::decompress; -IMHEX_PLUGIN_SETUP("Decompressing", "WerWolv", "Support for decompressing data") { - hex::log::debug("Using romfs: '{}'", romfs::name()); - - registerPatternLanguageFunctions(); -} - IMHEX_PLUGIN_FEATURES() { { "bzip2 Support", IMHEX_FEATURE_ENABLED(BZIP2) }, { "zlib Support", IMHEX_FEATURE_ENABLED(ZLIB) }, { "LZMA Support", IMHEX_FEATURE_ENABLED(LIBLZMA) }, { "zstd Support", IMHEX_FEATURE_ENABLED(ZSTD) }, -}; \ No newline at end of file +}; + +IMHEX_PLUGIN_SETUP("Decompressing", "WerWolv", "Support for decompressing data") { + hex::log::debug("Using romfs: '{}'", romfs::name()); + + registerPatternLanguageFunctions(); +} \ No newline at end of file