From 7a6d89d328f6da621d951fd59e13f2004be837af Mon Sep 17 00:00:00 2001 From: Dan Goodliffe Date: Fri, 6 Apr 2018 11:30:10 +0100 Subject: C++17 Remove all raw pointers and boost things now in the standard library from plugins and factory. --- libadhocutil/factory.h | 10 +++---- libadhocutil/factory.impl.h | 4 +-- libadhocutil/plugins.cpp | 11 ++----- libadhocutil/plugins.h | 36 +++++++++++----------- libadhocutil/plugins.impl.h | 43 ++++++++++++++------------- libadhocutil/unittests/testFactory.cpp | 4 --- libadhocutil/unittests/testPlugins.cpp | 18 +++++------ libadhocutil/unittests/testPluginsRuntime.cpp | 14 ++++----- 8 files changed, 66 insertions(+), 74 deletions(-) diff --git a/libadhocutil/factory.h b/libadhocutil/factory.h index 74f2a6b..4aaf335 100644 --- a/libadhocutil/factory.h +++ b/libadhocutil/factory.h @@ -17,7 +17,7 @@ namespace AdHoc { * Create a new instance of Base, overridden in a subclass to construct a new specific class. * @param p The parameters passed to Impl constructor. */ - virtual Base * create(const Params & ... p) const = 0; + virtual std::shared_ptr create(const Params & ... p) const = 0; /** * A factory for a concrete implementation of Base @@ -30,9 +30,9 @@ namespace AdHoc { * Create a new instance of Base implemented in Impl. * @param p The parameters passed to Impl constructor. */ - Base * create(const Params & ... p) const override + std::shared_ptr create(const Params & ... p) const override { - return new Impl(p...); + return std::make_shared(p...); } }; @@ -40,13 +40,13 @@ namespace AdHoc { * Helper to get the factory for a specific implementation. * @param name The name of the implementation. */ - static const Factory * get(const std::string & name); + static std::shared_ptr get(const std::string & name); /** * Helper to create a new instance from a specific factory. * @param name The name of the implementation. * @param p The parameters to pass to the constructor. */ - static Base * createNew(const std::string & name, const Params & ... p); + static std::shared_ptr createNew(const std::string & name, const Params & ... p); }; } diff --git a/libadhocutil/factory.impl.h b/libadhocutil/factory.impl.h index c257884..bd4ed38 100644 --- a/libadhocutil/factory.impl.h +++ b/libadhocutil/factory.impl.h @@ -9,14 +9,14 @@ namespace AdHoc { Factory::~Factory() = default; template - const Factory * + std::shared_ptr> Factory::get(const std::string & name) { return PluginManager::getDefault()->get(name)->implementation(); } template - Base * + std::shared_ptr Factory::createNew(const std::string & name, const Params & ... p) { return get(name)->create(p...); diff --git a/libadhocutil/plugins.cpp b/libadhocutil/plugins.cpp index 90d7b02..433b317 100644 --- a/libadhocutil/plugins.cpp +++ b/libadhocutil/plugins.cpp @@ -5,6 +5,7 @@ #include #include "compileTimeFormatter.h" #include "globalStatic.impl.h" +#include namespace std { bool @@ -13,12 +14,6 @@ namespace std { return a.hash_code() < b.hash_code(); } - bool - operator<(const AdHoc::PluginManager::PluginResolver & a, const AdHoc::PluginManager::PluginResolver & b) - { - return a.boost::function_base::get_vtable() < b.boost::function_base::get_vtable(); - } - std::ostream & operator<<(std::ostream & s, const std::type_info & t) { @@ -41,8 +36,6 @@ namespace AdHoc { { } - Plugin::~Plugin() = default; - AdHocFormatter(NoSuchPluginExceptionMsg, "No such plugin: %? of type %?"); NoSuchPluginException::NoSuchPluginException(const std::string & n, const std::type_info & t) : std::runtime_error(NoSuchPluginExceptionMsg::get(n, t)) @@ -87,7 +80,7 @@ namespace AdHoc { } void - PluginManager::add(PluginPtr p) + PluginManager::add(const PluginPtr & p) { auto prev = plugins->insert(p); if (!prev.second) { diff --git a/libadhocutil/plugins.h b/libadhocutil/plugins.h index 69d0182..0fab76e 100644 --- a/libadhocutil/plugins.h +++ b/libadhocutil/plugins.h @@ -1,9 +1,9 @@ #ifndef ADHOCUTIL_PLUGINS_H #define ADHOCUTIL_PLUGINS_H -#include -#include -#include +#include +#include +#include #include #include #include @@ -41,13 +41,13 @@ namespace AdHoc { public: /// Constructor taking name, filename and line of install. Plugin(const std::string &, const std::string &, int); - virtual ~Plugin(); + virtual ~Plugin() = default; /// Get the plugin type from the subclass. virtual const std::type_info & type() const = 0; /// Get the abstract base plugin implementation. - virtual AbstractPluginImplementation * implementation() const = 0; + virtual std::shared_ptr instance() const = 0; /// The name the plugin was installed with. const std::string name; @@ -56,7 +56,7 @@ namespace AdHoc { /// The line of file the plugin was installed in. const int lineno; }; - typedef boost::shared_ptr PluginPtr; + typedef std::shared_ptr PluginPtr; /// Thrown when a plugin with the same name and base is loaded into a manager. class DuplicatePluginException : public std::runtime_error { @@ -84,16 +84,18 @@ namespace AdHoc { class DLL_PUBLIC PluginOf : public Plugin { public: /// Constructor taking an instance and name, filename and line of install for Plugin. - PluginOf(T * t, const std::string & n, const std::string & f, int l); - ~PluginOf(); + PluginOf(const std::shared_ptr & t, const std::string & n, const std::string & f, int l); + ~PluginOf() = default; /// Get the type of this plugin. const std::type_info & type() const override; /// Get the implementation of this plugin. - T * implementation() const override; + std::shared_ptr implementation() const; + + std::shared_ptr instance() const override; private: - T * impl; + std::shared_ptr impl; }; /// Container for loaded plugins. @@ -101,13 +103,13 @@ namespace AdHoc { public: /// Callback definition to resolve a plugin type and name to a potential library /// containing an implementation. - typedef boost::function (const std::type_info &, const std::string &)> PluginResolver; + typedef std::function (const std::type_info &, const std::string &)> PluginResolver; PluginManager(); virtual ~PluginManager(); /// Install a plugin. - void add(PluginPtr); + void add(const PluginPtr &); /// Uninstall a plugin. void remove(const std::string &, const std::type_info &); /// Get a specific plugin. @@ -124,7 +126,7 @@ namespace AdHoc { * @param f Filename of plugin. * @param l Line number. */ - template void add(T * i, const std::string & n, const std::string & f, int l); + template void add(const std::shared_ptr & i, const std::string & n, const std::string & f, int l); /** * Uninstall a plugin. @@ -136,18 +138,18 @@ namespace AdHoc { * Get a specific plugin. * @param n Name of plugin. */ - template boost::shared_ptr> get(const std::string & n) const; + template std::shared_ptr> get(const std::string & n) const; /** * Get the implementation from specific plugin. * @param n Name of plugin. */ - template T * getImplementation(const std::string & n) const; + template std::shared_ptr getImplementation(const std::string & n) const; /** * Get all plugins of a given time. */ - template std::set>> getAll() const; + template std::set>> getAll() const; /** * The number of installed plugins. @@ -214,7 +216,7 @@ namespace AdHoc { namespace MAKE_UNIQUE(__plugin__) { \ static void InstallPlugin() __attribute__((constructor(102))); \ void InstallPlugin() { \ - ::AdHoc::PluginManager::getDefault()->add(new Implementation(), Name, __FILE__, __LINE__); \ + ::AdHoc::PluginManager::getDefault()->add(std::make_shared(), Name, __FILE__, __LINE__); \ } \ static void UninstallPlugin() __attribute__((destructor(102))); \ void UninstallPlugin() { \ diff --git a/libadhocutil/plugins.impl.h b/libadhocutil/plugins.impl.h index 8b64002..6f8da05 100644 --- a/libadhocutil/plugins.impl.h +++ b/libadhocutil/plugins.impl.h @@ -5,18 +5,12 @@ namespace AdHoc { template - PluginOf::PluginOf(T * t, const std::string & n, const std::string & f, int l) : + PluginOf::PluginOf(const std::shared_ptr & t, const std::string & n, const std::string & f, int l) : Plugin(n, f, l), impl(t) { } - template - PluginOf::~PluginOf() - { - delete impl; - } - /// Get the type of this plugin. template const std::type_info & @@ -27,17 +21,24 @@ namespace AdHoc { /// Get the implementation of this plugin. template - T * + std::shared_ptr PluginOf::implementation() const { return impl; } + template + std::shared_ptr + PluginOf::instance() const + { + return impl; + } + template void - PluginManager::add(T * i, const std::string & n, const std::string & f, int l) + PluginManager::add(const std::shared_ptr & i, const std::string & n, const std::string & f, int l) { - add(PluginPtr(new PluginOf(i, n, f, l))); + add(std::make_shared>(i, n, f, l)); } template @@ -48,26 +49,26 @@ namespace AdHoc { } template - boost::shared_ptr> + std::shared_ptr> PluginManager::get(const std::string & n) const { - return boost::dynamic_pointer_cast>(get(n, typeid(T))); + return std::dynamic_pointer_cast>(get(n, typeid(T))); } template - T * + std::shared_ptr PluginManager::getImplementation(const std::string & n) const { - return get(n)->implementation(); + return std::static_pointer_cast(get(n)->implementation()); } template - std::set>> + std::set>> PluginManager::getAll() const { - std::set>> all; + std::set>> all; for(const auto & p : getAll(typeid(T))) { - if (auto tp = boost::dynamic_pointer_cast>(p)) { + if (auto tp = std::dynamic_pointer_cast>(p)) { all.insert(tp); } } @@ -91,11 +92,11 @@ namespace AdHoc { #define INSTANTIATEPLUGINOF(...) \ template class AdHoc::PluginOf<__VA_ARGS__>; \ - template void AdHoc::PluginManager::add<__VA_ARGS__>(__VA_ARGS__ *, const std::string &, const std::string &, int); \ + template void AdHoc::PluginManager::add<__VA_ARGS__>(const std::shared_ptr<__VA_ARGS__> &, const std::string &, const std::string &, int); \ template void AdHoc::PluginManager::remove<__VA_ARGS__>(const std::string &); \ - template boost::shared_ptr> AdHoc::PluginManager::get<__VA_ARGS__>(const std::string &) const; \ - template __VA_ARGS__ * AdHoc::PluginManager::getImplementation<__VA_ARGS__>(const std::string &) const; \ - template std::set>> AdHoc::PluginManager::getAll<__VA_ARGS__>() const; \ + template std::shared_ptr> AdHoc::PluginManager::get<__VA_ARGS__>(const std::string &) const; \ + template std::shared_ptr<__VA_ARGS__> AdHoc::PluginManager::getImplementation<__VA_ARGS__>(const std::string &) const; \ + template std::set>> AdHoc::PluginManager::getAll<__VA_ARGS__>() const; \ template void AdHoc::PluginManager::addResolver<__VA_ARGS__>(const AdHoc::PluginManager::PluginResolver & f); \ template void AdHoc::PluginManager::removeResolver<__VA_ARGS__>(); \ diff --git a/libadhocutil/unittests/testFactory.cpp b/libadhocutil/unittests/testFactory.cpp index 10e2013..0eb959c 100644 --- a/libadhocutil/unittests/testFactory.cpp +++ b/libadhocutil/unittests/testFactory.cpp @@ -88,9 +88,6 @@ BOOST_AUTO_TEST_CASE( create ) BOOST_REQUIRE(i1 != i2); BOOST_REQUIRE(i1 != i3); BOOST_REQUIRE(i2 != i3); - delete i1; - delete i2; - delete i3; } BOOST_AUTO_TEST_CASE( createNew ) @@ -98,6 +95,5 @@ BOOST_AUTO_TEST_CASE( createNew ) std::string n; auto i = BaseThingFactory::createNew("a", 1, &n); BOOST_REQUIRE(i); - delete i; } diff --git a/libadhocutil/unittests/testPlugins.cpp b/libadhocutil/unittests/testPlugins.cpp index 81d7ec1..84d00c7 100644 --- a/libadhocutil/unittests/testPlugins.cpp +++ b/libadhocutil/unittests/testPlugins.cpp @@ -31,10 +31,10 @@ BOOST_AUTO_TEST_CASE( getAll ) { auto all = PluginManager::getDefault()->getAll(); BOOST_REQUIRE_EQUAL(1, all.size()); - auto base = (*all.begin())->implementation(); + auto base = (*all.begin())->instance(); BOOST_REQUIRE(base); - BOOST_REQUIRE(dynamic_cast(base)); - BOOST_REQUIRE(dynamic_cast(base)); + BOOST_REQUIRE(std::dynamic_pointer_cast(base)); + BOOST_REQUIRE(std::dynamic_pointer_cast(base)); auto allOf = PluginManager::getDefault()->getAll(); BOOST_REQUIRE_EQUAL(1, allOf.size()); } @@ -42,10 +42,10 @@ BOOST_AUTO_TEST_CASE( getAll ) BOOST_AUTO_TEST_CASE( addManual ) { auto o1 = PluginManager::getDefault()->get("ImplOfThing"); - PluginManager::getDefault()->add(PluginPtr(new PluginOf(new ImplOfThing(), "custom1", __FILE__, __LINE__))); + PluginManager::getDefault()->add(std::make_shared>(std::make_shared(), "custom1", __FILE__, __LINE__)); BOOST_REQUIRE_EQUAL(2, PluginManager::getDefault()->count()); auto c1 = PluginManager::getDefault()->get("custom1"); - PluginManager::getDefault()->add(new ImplOfThing(), "custom2", __FILE__, __LINE__); + PluginManager::getDefault()->add(std::make_shared(), "custom2", __FILE__, __LINE__); BOOST_REQUIRE_EQUAL(3, PluginManager::getDefault()->count()); auto c2 = PluginManager::getDefault()->get("custom2"); auto o2 = PluginManager::getDefault()->get("ImplOfThing"); @@ -75,18 +75,18 @@ BOOST_AUTO_TEST_CASE( removeManual ) BOOST_AUTO_TEST_CASE( nameAndTypeClash ) { // Same name, different type - PluginManager::getDefault()->add(new OtherImpl(), "ImplOfThing", __FILE__, __LINE__); + PluginManager::getDefault()->add(std::make_shared(), "ImplOfThing", __FILE__, __LINE__); // Different name, same type - PluginManager::getDefault()->add(new ImplOfThing(), "Different", __FILE__, __LINE__); + PluginManager::getDefault()->add(std::make_shared(), "Different", __FILE__, __LINE__); // Same name, same thing, should error - BOOST_REQUIRE_THROW(PluginManager::getDefault()->add(new OtherImplOfThing(), "ImplOfThing", __FILE__, __LINE__), DuplicatePluginException); + BOOST_REQUIRE_THROW(PluginManager::getDefault()->add(std::make_shared(), "ImplOfThing", __FILE__, __LINE__), DuplicatePluginException); PluginManager::getDefault()->remove("ImplOfThing"); PluginManager::getDefault()->remove("Different"); } BOOST_AUTO_TEST_CASE( otherTypes ) { - PluginManager::getDefault()->add(new OtherImpl(), "ImplOfThing", __FILE__, __LINE__); + PluginManager::getDefault()->add(std::make_shared(), "ImplOfThing", __FILE__, __LINE__); BOOST_REQUIRE_EQUAL(2, PluginManager::getDefault()->count()); BOOST_REQUIRE_EQUAL(2, PluginManager::getDefault()->getAll().size()); BOOST_REQUIRE_EQUAL(1, PluginManager::getDefault()->getAll().size()); diff --git a/libadhocutil/unittests/testPluginsRuntime.cpp b/libadhocutil/unittests/testPluginsRuntime.cpp index 68d94d5..654c6ad 100644 --- a/libadhocutil/unittests/testPluginsRuntime.cpp +++ b/libadhocutil/unittests/testPluginsRuntime.cpp @@ -11,9 +11,9 @@ using namespace AdHoc; auto lib = rootDir / "bin" / buildVariant / "libutilTestClasses.so"; -static boost::optional nullResolver(const std::type_info &, const std::string &); -static boost::optional badResolver(const std::type_info &, const std::string &); -static boost::optional goodResolver(const std::type_info &, const std::string &); +static std::optional nullResolver(const std::type_info &, const std::string &); +static std::optional badResolver(const std::type_info &, const std::string &); +static std::optional goodResolver(const std::type_info &, const std::string &); BOOST_AUTO_TEST_CASE( ready ) { @@ -35,19 +35,19 @@ BOOST_AUTO_TEST_CASE( loadAndUnloadlib ) BOOST_REQUIRE_EQUAL(0, AdHoc::PluginManager::getDefault()->getAll().size()); } -boost::optional +std::optional nullResolver(const std::type_info &, const std::string &) { - return boost::optional(); + return {}; } -boost::optional +std::optional badResolver(const std::type_info &, const std::string &) { return std::string("dontexist"); } -boost::optional +std::optional goodResolver(const std::type_info & t, const std::string & n) { BOOST_REQUIRE_EQUAL(typeid(BaseThing), t); -- cgit v1.2.3