diff --git a/src/lib/meta/function-erasure.hpp b/src/lib/meta/function-erasure.hpp index 460143baf..f86de74b9 100644 --- a/src/lib/meta/function-erasure.hpp +++ b/src/lib/meta/function-erasure.hpp @@ -55,6 +55,7 @@ #include "lib/util.hpp" #include "lib/error.hpp" +#include "lib/bool-checkable.hpp" #include @@ -76,7 +77,7 @@ namespace typelist{ * using the templated \c getFun() * * @param FH policy to control the implementation. - * In most cases, you should use "StoreFunction" + * In most cases, you should use "StoreFunction" * @note not statically typesafe. Depending on * the specified policy, it \em might be * run-time typesafe. @@ -91,40 +92,19 @@ namespace typelist{ { } }; - + /* ====== Policy classes ====== */ - - template - struct BoolCheckable - { - typedef bool (T::*ValidityCheck)() const; - typedef ValidityCheck _unspecified_bool_type; - - /** implicit conversion to "bool" */ - operator _unspecified_bool_type() const ///< never throws - { - ValidityCheck isValid (&T::isValid); - T const& obj = static_cast (*this); - return (obj.*isValid)()? isValid : 0; - } - - bool operator! () const ///< never throws - { - ValidityCheck isValid (&T::isValid); - T const& obj = static_cast (*this); - return !(obj.*isValid)(); - } - - }; - + /** * Policy for FunErasure: store an embedded tr1::function * Using this policy allows to store arbitrary complex functor objects * embedded within a neutral container and retrieving them later type-safe. - * The price to pay is vtable access and heap storage of function arguments. + * The price to pay is vtable access and heap storage of function arguments. + * + * @note the bool conversion and #isValid are highly implementation dependent */ class StoreFunction -// : public BoolCheckable + : public lib::BoolCheckable { /** Helper: type erasure */ struct Holder @@ -181,7 +161,7 @@ namespace typelist{ } bool - isValid() const + isValid() const ///< @note implementation dependent!! { return reinterpret_cast (holder_.storage_[0]); } @@ -195,6 +175,7 @@ namespace typelist{ * The price to pay is vtable access. */ class StoreFunPtr + : public lib::BoolCheckable { /** Helper: type erasure */ struct Holder @@ -241,6 +222,13 @@ namespace typelist{ REQUIRE (INSTANCEOF (FunctionHolder, &holder_)); return static_cast&> (holder_).get(); } + + + bool + isValid() const + { + return holder_.fP_; + } }; @@ -250,6 +238,7 @@ namespace typelist{ * and to retrieve it without overhead, but also without safety. */ class StoreUncheckedFunPtr + : public lib::BoolCheckable { void *funP_; @@ -271,6 +260,13 @@ namespace typelist{ { return *reinterpret_cast (funP_); } + + + bool + isValid() const + { + return funP_; + } }; diff --git a/src/proc/control/command-mutation.hpp b/src/proc/control/command-mutation.hpp index df32cfe22..f0f77d704 100644 --- a/src/proc/control/command-mutation.hpp +++ b/src/proc/control/command-mutation.hpp @@ -84,7 +84,7 @@ namespace control { close (CmdClosure& cmdClosure) { REQUIRE (!clo_, "Lifecycle error: already closed over the arguments"); -// REQUIRE (func_, "Param error: not bound to a valid function"); + REQUIRE (func_, "Param error: not bound to a valid function"); func_ = cmdClosure.bindArguments(func_); clo_ = &cmdClosure; return *this; @@ -117,7 +117,7 @@ namespace control { virtual bool isValid () const { -// return func_ && clo_; + return func_ && clo_; } void @@ -177,7 +177,7 @@ namespace control { close (CmdClosure& cmdClosure) { REQUIRE (!memento_, "Lifecycle error: already closed over the arguments"); -// REQUIRE (captureFunc_, "Param error: not bound to a valid function"); + REQUIRE (captureFunc_, "Param error: not bound to a valid function"); // create a special state closure, which can later on store the captured undo state (memento) scoped_ptr stateClosure (new MementoClosure (captureFunc_)); @@ -213,7 +213,7 @@ namespace control { virtual bool isValid () const { -// return Mutation::isValid() && captureFunc_ && memento_; + return Mutation::isValid() && captureFunc_ && memento_; } diff --git a/tests/lib/meta/function-erasure-test.cpp b/tests/lib/meta/function-erasure-test.cpp index 6d98582f1..43320c453 100644 --- a/tests/lib/meta/function-erasure-test.cpp +++ b/tests/lib/meta/function-erasure-test.cpp @@ -212,10 +212,10 @@ namespace test { typedef typename BuildEmptyHolder::Type EmptyHolder; EmptyHolder emptyHolder; -// ASSERT (!emptyHolder); -// ASSERT ( h1 ); -// ASSERT ( h2 ); -// ASSERT ( h3 ); + ASSERT (!emptyHolder); + ASSERT ( h1 ); + ASSERT ( h2 ); + ASSERT ( h3 ); }