summaryrefslogtreecommitdiff
path: root/base/callback.h
diff options
context:
space:
mode:
authorJakub Pawlowski <jpawlowski@google.com>2017-03-14 10:55:53 -0700
committerJakub Pawlowski <jpawlowski@google.com>2017-12-19 07:47:37 -0800
commitbf8c17f71511c1e90cd8cccfe71f0852c566bd3b (patch)
treeb5603968c3907c8b41594f2a2b0f15475406f94d /base/callback.h
parent9b3f4a254c327005c91c1eb094062cdefe5f0553 (diff)
downloadlibchrome-bf8c17f71511c1e90cd8cccfe71f0852c566bd3b.tar.gz
Uprev the library to r462023 from Chromium
This merge was done against r462023 which corresponds to git commit 32eb7c31af9cab6231f0d3d05206072079177605 from Apr 05, 2017 Change-Id: I70bf77fcb3215da3e17f997752bfdad7d4e6e1c9
Diffstat (limited to 'base/callback.h')
-rw-r--r--base/callback.h90
1 files changed, 22 insertions, 68 deletions
diff --git a/base/callback.h b/base/callback.h
index 40bd5208a8..c91e1a88d3 100644
--- a/base/callback.h
+++ b/base/callback.h
@@ -21,71 +21,6 @@ namespace base {
namespace internal {
-template <typename CallbackType>
-struct IsOnceCallback : std::false_type {};
-
-template <typename Signature>
-struct IsOnceCallback<OnceCallback<Signature>> : std::true_type {};
-
-// RunMixin provides different variants of `Run()` function to `Callback<>`
-// based on the type of callback.
-template <typename CallbackType>
-class RunMixin;
-
-// Specialization for OnceCallback.
-template <typename R, typename... Args>
-class RunMixin<OnceCallback<R(Args...)>> {
- private:
- using CallbackType = OnceCallback<R(Args...)>;
-
- public:
- using PolymorphicInvoke = R(*)(internal::BindStateBase*, Args&&...);
-
- R Run(Args... /* args */) const & {
- // Note: even though this static_assert will trivially always fail, it
- // cannot be simply replaced with static_assert(false, ...) because:
- // - Per [dcl.dcl]/p4, a program is ill-formed if the constant-expression
- // argument does not evaluate to true.
- // - Per [temp.res]/p8, if no valid specialization can be generated for a
- // template definition, and that template is not instantiated, the
- // template definition is ill-formed, no diagnostic required.
- // These two clauses, taken together, would allow a conforming C++ compiler
- // to immediately reject static_assert(false, ...), even inside an
- // uninstantiated template.
- static_assert(!IsOnceCallback<CallbackType>::value,
- "OnceCallback::Run() may only be invoked on a non-const "
- "rvalue, i.e. std::move(callback).Run().");
- }
-
- R Run(Args... args) && {
- // Move the callback instance into a local variable before the invocation,
- // that ensures the internal state is cleared after the invocation.
- // It's not safe to touch |this| after the invocation, since running the
- // bound function may destroy |this|.
- CallbackType cb = static_cast<CallbackType&&>(*this);
- PolymorphicInvoke f =
- reinterpret_cast<PolymorphicInvoke>(cb.polymorphic_invoke());
- return f(cb.bind_state_.get(), std::forward<Args>(args)...);
- }
-};
-
-// Specialization for RepeatingCallback.
-template <typename R, typename... Args>
-class RunMixin<RepeatingCallback<R(Args...)>> {
- private:
- using CallbackType = RepeatingCallback<R(Args...)>;
-
- public:
- using PolymorphicInvoke = R(*)(internal::BindStateBase*, Args&&...);
-
- R Run(Args... args) const {
- const CallbackType& cb = static_cast<const CallbackType&>(*this);
- PolymorphicInvoke f =
- reinterpret_cast<PolymorphicInvoke>(cb.polymorphic_invoke());
- return f(cb.bind_state_.get(), std::forward<Args>(args)...);
- }
-};
-
template <typename From, typename To>
struct IsCallbackConvertible : std::false_type {};
@@ -100,14 +35,14 @@ template <typename R,
internal::CopyMode copy_mode,
internal::RepeatMode repeat_mode>
class Callback<R(Args...), copy_mode, repeat_mode>
- : public internal::CallbackBase<copy_mode>,
- public internal::RunMixin<Callback<R(Args...), copy_mode, repeat_mode>> {
+ : public internal::CallbackBase<copy_mode> {
public:
static_assert(repeat_mode != internal::RepeatMode::Once ||
copy_mode == internal::CopyMode::MoveOnly,
"OnceCallback must be MoveOnly.");
using RunType = R(Args...);
+ using PolymorphicInvoke = R (*)(internal::BindStateBase*, Args&&...);
Callback() : internal::CallbackBase<copy_mode>(nullptr) {}
@@ -135,7 +70,26 @@ class Callback<R(Args...), copy_mode, repeat_mode>
return this->EqualsInternal(other);
}
- friend class internal::RunMixin<Callback>;
+ R Run(Args... args) const & {
+ static_assert(repeat_mode == internal::RepeatMode::Repeating,
+ "OnceCallback::Run() may only be invoked on a non-const "
+ "rvalue, i.e. std::move(callback).Run().");
+
+ PolymorphicInvoke f =
+ reinterpret_cast<PolymorphicInvoke>(this->polymorphic_invoke());
+ return f(this->bind_state_.get(), std::forward<Args>(args)...);
+ }
+
+ R Run(Args... args) && {
+ // Move the callback instance into a local variable before the invocation,
+ // that ensures the internal state is cleared after the invocation.
+ // It's not safe to touch |this| after the invocation, since running the
+ // bound function may destroy |this|.
+ Callback cb = std::move(*this);
+ PolymorphicInvoke f =
+ reinterpret_cast<PolymorphicInvoke>(cb.polymorphic_invoke());
+ return f(cb.bind_state_.get(), std::forward<Args>(args)...);
+ }
};
} // namespace base