diff --git a/src/lib/depend-inject.hpp b/src/lib/depend-inject.hpp index 11342c059..78d586fdd 100644 --- a/src/lib/depend-inject.hpp +++ b/src/lib/depend-inject.hpp @@ -95,8 +95,8 @@ ** @warning there is a known coherency breach in "emergency shutdown": When a ** subsystem collapses unexpectedly, its root handler signals the subsystem ** runner to initiate emergency shutdown. However, the collapsed subsystem - ** is already defunct at that point, which breaks the the general contract - ** of prerequisite subsystems to be available in operative mode. Lumiera + ** is already defunct at that point, which breaks the general contract of + ** prerequisite subsystems to be available in operative mode. Lumiera ** is not built as a resilient service in that respect, but we also ** mandate for any parts not to cache essential work results in ** transient memory; actions are logged and performed for @@ -262,7 +262,7 @@ namespace lib { std::unique_ptr mock_; SRV* origInstance_; - DependencyFactory origFactory_; + Factory origFactory_; public: Local() @@ -286,7 +286,8 @@ namespace lib { ~Local() { restoreOriginalFactory (origInstance_, move(origFactory_)); - } + origFactory_ = Factory{}; + } // clear possibly leftover deleter explicit operator bool() const @@ -341,7 +342,7 @@ namespace lib { static_assert (meta::_Fun(), "Need a Lambda or Function object to create a heap allocated instance"); - using Fun = typename meta::_Fun::Functor; // suitable type to store for later invocation + using Fun = typename meta::_Fun::Functor; // suitable type to store for later invocation using Res = typename meta::_Fun::Ret; using Sub = typename meta::Strip::TypePlain; diff --git a/src/lib/depend2.hpp b/src/lib/depend2.hpp index 4fef8ba27..1db17c5a7 100644 --- a/src/lib/depend2.hpp +++ b/src/lib/depend2.hpp @@ -70,8 +70,8 @@ ** ## Implementation and performance ** ** Due to this option for flexible configuration, the implementation can not be built - ** as Meyer's Singleton. Rather, Double Checked Locking of a Mutex is combined with an - ** std::atomic to work around the known (rather theoretical) problems of this pattern. + ** as Meyer's Singleton. Rather, Double Checked Locking of a Mutex is combined with + ** an std::atomic to work around the known (rather theoretical) concurrency problems. ** Microbenchmarks indicate that this implementation technique ranges close to the ** speed of a direct access to an already existing object; in the fully optimised ** variant it was found to be roughly at ≈ 1ns and thus about 3 to 4 times slower @@ -107,10 +107,17 @@ namespace lib { /** * Helper to abstract creation and lifecycle of a dependency + * Holds a configurable constructor function and optionally + * an automatically invoked deleter function. + * @note DependencyFactory can be declared friend to indicate + * the expected way to invoke an otherwise private ctor. + * This is a classical idiom for singletons. + * @see lib::Depend + * @see lib::DependInject */ template class DependencyFactory -// : util::MoveAssign //////////////////////////////////////////////TICKET #1059 : GCC-4.9 stubbornly picks the copy assignment + : util::NonCopyable { using Creator = std::function; using Deleter = std::function; @@ -211,6 +218,7 @@ namespace lib { { return new TAR; } + template static meta::enable_if, ABS* > @@ -254,20 +262,23 @@ namespace lib { template class Depend { + using Instance = std::atomic; using Factory = DependencyFactory; using Lock = ClassLock; - static std::atomic instance; - static DependencyFactory factory; + /* === shared per type === */ + static Instance instance; + static Factory factory; friend class DependInject; public: - /** Interface to be used by clients for retrieving the service instance. - * Manages the instance creation, lifecycle and access in multithreaded context. - * @return instance of class `SRV`. When used in default configuration, - * this service instance is a singleton + /** + * Interface to be used by clients for retrieving the service instance. + * Manages the instance creation, lifecycle and access in multithreaded context. + * @return instance of class `SRV`. When used in default configuration, + * the returned service instance is a singleton. */ SRV& operator() () diff --git a/wiki/thinkPad.ichthyo.mm b/wiki/thinkPad.ichthyo.mm index 024a8b9d0..e99841c6e 100644 --- a/wiki/thinkPad.ichthyo.mm +++ b/wiki/thinkPad.ichthyo.mm @@ -27697,9 +27697,9 @@ - + - + @@ -27796,18 +27796,47 @@ - + - + - + - + + + + + + + +

+ zwar wird beim Löschen des Mock +

+

+ die ursprüngliche Factory wieder an ihren Platz zurückgeschoben, +

+

+ aber niemand sagt, daß ein Move auch wirklich ein Move (swap) ist. +

+

+ Muß daher diese leer gewordene temporäre Factory explizit auf Default-Zustand zurücksetzen, +

+

+ damit nicht doch noch der Deleter läuft. +

+ + +
+ +
+ + +