aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--configure.ac19
-rw-r--r--src/libstrongswan/plugins/plugin_loader.c62
-rw-r--r--src/libstrongswan/plugins/plugin_loader.h10
3 files changed, 87 insertions, 4 deletions
diff --git a/configure.ac b/configure.ac
index 56738bdf3..07df3a672 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1,5 +1,5 @@
#
-# Copyright (C) 2007-2015 Tobias Brunner
+# Copyright (C) 2007-2017 Tobias Brunner
# Copyright (C) 2006-2016 Andreas Steffen
# Copyright (C) 2006-2014 Martin Willi
# HSR Hochschule fuer Technik Rapperswil
@@ -1303,6 +1303,19 @@ AM_CONDITIONAL(PYTHON_EGGS_INSTALL, [test "x$python_eggs_install" = xtrue])
AM_CONDITIONAL(PERL_CPAN_INSTALL, [test "x$perl_cpan_install" = xtrue])
+AC_CACHE_CHECK(
+ [if plugin constructors should be resolved statically],
+ [ss_cv_static_plugin_constructors],
+ [if test x$monolithic = xtrue -a x$enable_static = xyes; then
+ ss_cv_static_plugin_constructors=yes
+ else
+ ss_cv_static_plugin_constructors="no (enabled for static, monolithic builds)"
+ fi]
+)
+if test "x$ss_cv_static_plugin_constructors" = xyes; then
+ static_plugin_constructors=true
+fi
+
# ===============================================
# collect plugin list for strongSwan components
# ===============================================
@@ -1678,6 +1691,7 @@ AM_CONDITIONAL(USE_IMCV, test x$imcv = xtrue)
AM_CONDITIONAL(USE_TROUSERS, test x$tss_trousers = xtrue)
AM_CONDITIONAL(USE_TSS2, test x$tss_tss2 = xtrue)
AM_CONDITIONAL(MONOLITHIC, test x$monolithic = xtrue)
+AM_CONDITIONAL(STATIC_PLUGIN_CONSTRUCTORS, test x$static_plugin_constructors = xtrue)
AM_CONDITIONAL(USE_SILENT_RULES, test x$enable_silent_rules = xyes)
AM_CONDITIONAL(COVERAGE, test x$coverage = xtrue)
AM_CONDITIONAL(USE_DBGHELP, test x$dbghelp_backtraces = xtrue)
@@ -1709,6 +1723,9 @@ fi
if test x$monolithic = xtrue; then
AC_DEFINE([MONOLITHIC], [], [monolithic build embedding plugins])
fi
+if test x$static_plugin_constructors = xtrue; then
+ AC_DEFINE([STATIC_PLUGIN_CONSTRUCTORS], [], [static plugin constructors])
+fi
if test x$ikev1 = xtrue; then
AC_DEFINE([USE_IKEV1], [], [support for IKEv1 protocol])
fi
diff --git a/src/libstrongswan/plugins/plugin_loader.c b/src/libstrongswan/plugins/plugin_loader.c
index e4698fac0..e78762b2c 100644
--- a/src/libstrongswan/plugins/plugin_loader.c
+++ b/src/libstrongswan/plugins/plugin_loader.c
@@ -40,6 +40,13 @@ typedef struct registered_feature_t registered_feature_t;
typedef struct provided_feature_t provided_feature_t;
typedef struct plugin_entry_t plugin_entry_t;
+#ifdef STATIC_PLUGIN_CONSTRUCTORS
+/**
+ * Statically registered constructors
+ */
+static hashtable_t *plugin_constructors = NULL;
+#endif
+
/**
* private data of plugin_loader
*/
@@ -298,6 +305,46 @@ static plugin_t *static_features_create(const char *name,
return &this->public;
}
+#ifdef STATIC_PLUGIN_CONSTRUCTORS
+/*
+ * Described in header.
+ */
+void plugin_constructor_register(char *name, void *constructor)
+{
+ bool old = FALSE;
+
+ if (lib && lib->leak_detective)
+ {
+ old = lib->leak_detective->set_state(lib->leak_detective, FALSE);
+ }
+
+ if (!plugin_constructors)
+ {
+ chunk_hash_seed();
+ plugin_constructors = hashtable_create(hashtable_hash_str,
+ hashtable_equals_str, 32);
+ }
+ if (constructor)
+ {
+ plugin_constructors->put(plugin_constructors, name, constructor);
+ }
+ else
+ {
+ plugin_constructors->remove(plugin_constructors, name);
+ if (!plugin_constructors->get_count(plugin_constructors))
+ {
+ plugin_constructors->destroy(plugin_constructors);
+ plugin_constructors = NULL;
+ }
+ }
+
+ if (lib && lib->leak_detective)
+ {
+ lib->leak_detective->set_state(lib->leak_detective, old);
+ }
+}
+#endif
+
/**
* create a plugin
* returns: NOT_FOUND, if the constructor was not found
@@ -309,7 +356,7 @@ static status_t create_plugin(private_plugin_loader_t *this, void *handle,
{
char create[128];
plugin_t *plugin;
- plugin_constructor_t constructor;
+ plugin_constructor_t constructor = NULL;
if (snprintf(create, sizeof(create), "%s_plugin_create",
name) >= sizeof(create))
@@ -317,8 +364,17 @@ static status_t create_plugin(private_plugin_loader_t *this, void *handle,
return FAILED;
}
translate(create, "-", "_");
- constructor = dlsym(handle, create);
- if (constructor == NULL)
+#ifdef STATIC_PLUGIN_CONSTRUCTORS
+ if (plugin_constructors)
+ {
+ constructor = plugin_constructors->get(plugin_constructors, name);
+ }
+ if (!constructor)
+#endif
+ {
+ constructor = dlsym(handle, create);
+ }
+ if (!constructor)
{
return NOT_FOUND;
}
diff --git a/src/libstrongswan/plugins/plugin_loader.h b/src/libstrongswan/plugins/plugin_loader.h
index 6be6a909c..92a860615 100644
--- a/src/libstrongswan/plugins/plugin_loader.h
+++ b/src/libstrongswan/plugins/plugin_loader.h
@@ -168,4 +168,14 @@ plugin_loader_t *plugin_loader_create();
*/
void plugin_loader_add_plugindirs(char *basedir, char *plugins);
+#ifdef STATIC_PLUGIN_CONSTRUCTORS
+/**
+ * Register a plugin constructor in case of static builds.
+ *
+ * @param name name of the plugin
+ * @param constructor constructor to register (set to NULL to unregister)
+ */
+void plugin_constructor_register(char *name, void *constructor);
+#endif
+
#endif /** PLUGIN_LOADER_H_ @}*/