1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
11 #include "base/callback.h"
12 #include "base/macros.h"
13 #include "base/memory/ptr_util.h"
14 #include "base/memory/ref_counted.h"
15 #include "base/memory/weak_ptr.h"
16 #include "base/test/bind_test_util.h"
17 #include "base/test/gtest_util.h"
18 #include "build/build_config.h"
19 #include "testing/gmock/include/gmock/gmock.h"
20 #include "testing/gtest/include/gtest/gtest.h"
22 using ::testing::AnyNumber;
23 using ::testing::ByMove;
24 using ::testing::Mock;
25 using ::testing::Return;
26 using ::testing::StrictMock;
38 MOCK_METHOD0(VoidMethod0, void());
39 MOCK_CONST_METHOD0(VoidConstMethod0, void());
41 MOCK_METHOD0(IntMethod0, int());
42 MOCK_CONST_METHOD0(IntConstMethod0, int());
44 MOCK_METHOD1(VoidMethodWithIntArg, void(int));
45 MOCK_METHOD0(UniquePtrMethod0, std::unique_ptr<int>());
48 // Particularly important in this test to ensure no copies are made.
49 DISALLOW_COPY_AND_ASSIGN(NoRef);
52 class HasRef : public NoRef {
56 MOCK_CONST_METHOD0(AddRef, void());
57 MOCK_CONST_METHOD0(Release, bool());
58 MOCK_CONST_METHOD0(HasAtLeastOneRef, bool());
61 // Particularly important in this test to ensure no copies are made.
62 DISALLOW_COPY_AND_ASSIGN(HasRef);
65 class HasRefPrivateDtor : public HasRef {
67 ~HasRefPrivateDtor() = default;
70 static const int kParentValue = 1;
71 static const int kChildValue = 2;
75 void AddRef() const {}
76 void Release() const {}
77 bool HasAtLeastOneRef() const { return true; }
78 virtual void VirtualSet() { value = kParentValue; }
79 void NonVirtualSet() { value = kParentValue; }
83 class Child : public Parent {
85 void VirtualSet() override { value = kChildValue; }
86 void NonVirtualSet() { value = kChildValue; }
91 virtual void VirtualSet() { value = kParentValue; }
92 void NonVirtualSet() { value = kParentValue; }
96 class NoRefChild : public NoRefParent {
97 void VirtualSet() override { value = kChildValue; }
98 void NonVirtualSet() { value = kChildValue; }
101 // Used for probing the number of copies and moves that occur if a type must be
102 // coerced during argument forwarding in the Run() methods.
103 struct DerivedCopyMoveCounter {
104 DerivedCopyMoveCounter(int* copies,
106 int* move_constructs,
110 move_constructs_(move_constructs),
111 move_assigns_(move_assigns) {}
114 int* move_constructs_;
118 // Used for probing the number of copies and moves in an argument.
119 class CopyMoveCounter {
121 CopyMoveCounter(int* copies,
123 int* move_constructs,
127 move_constructs_(move_constructs),
128 move_assigns_(move_assigns) {}
130 CopyMoveCounter(const CopyMoveCounter& other)
131 : copies_(other.copies_),
132 assigns_(other.assigns_),
133 move_constructs_(other.move_constructs_),
134 move_assigns_(other.move_assigns_) {
138 CopyMoveCounter(CopyMoveCounter&& other)
139 : copies_(other.copies_),
140 assigns_(other.assigns_),
141 move_constructs_(other.move_constructs_),
142 move_assigns_(other.move_assigns_) {
143 (*move_constructs_)++;
146 // Probing for copies from coercion.
147 explicit CopyMoveCounter(const DerivedCopyMoveCounter& other)
148 : copies_(other.copies_),
149 assigns_(other.assigns_),
150 move_constructs_(other.move_constructs_),
151 move_assigns_(other.move_assigns_) {
155 // Probing for moves from coercion.
156 explicit CopyMoveCounter(DerivedCopyMoveCounter&& other)
157 : copies_(other.copies_),
158 assigns_(other.assigns_),
159 move_constructs_(other.move_constructs_),
160 move_assigns_(other.move_assigns_) {
161 (*move_constructs_)++;
164 const CopyMoveCounter& operator=(const CopyMoveCounter& rhs) {
165 copies_ = rhs.copies_;
166 assigns_ = rhs.assigns_;
167 move_constructs_ = rhs.move_constructs_;
168 move_assigns_ = rhs.move_assigns_;
175 const CopyMoveCounter& operator=(CopyMoveCounter&& rhs) {
176 copies_ = rhs.copies_;
177 assigns_ = rhs.assigns_;
178 move_constructs_ = rhs.move_constructs_;
179 move_assigns_ = rhs.move_assigns_;
193 int* move_constructs_;
197 // Used for probing the number of copies in an argument. The instance is a
198 // copyable and non-movable type.
201 CopyCounter(int* copies, int* assigns)
202 : counter_(copies, assigns, nullptr, nullptr) {}
203 CopyCounter(const CopyCounter& other) = default;
204 CopyCounter& operator=(const CopyCounter& other) = default;
206 explicit CopyCounter(const DerivedCopyMoveCounter& other) : counter_(other) {}
208 int copies() const { return counter_.copies(); }
211 CopyMoveCounter counter_;
214 // Used for probing the number of moves in an argument. The instance is a
215 // non-copyable and movable type.
218 MoveCounter(int* move_constructs, int* move_assigns)
219 : counter_(nullptr, nullptr, move_constructs, move_assigns) {}
220 MoveCounter(MoveCounter&& other) : counter_(std::move(other.counter_)) {}
221 MoveCounter& operator=(MoveCounter&& other) {
222 counter_ = std::move(other.counter_);
226 explicit MoveCounter(DerivedCopyMoveCounter&& other)
227 : counter_(std::move(other)) {}
230 CopyMoveCounter counter_;
233 class DeleteCounter {
235 explicit DeleteCounter(int* deletes)
236 : deletes_(deletes) {
243 void VoidMethod0() {}
249 template <typename T>
250 T PassThru(T scoper) {
254 // Some test functions that we can Bind to.
255 template <typename T>
256 T PolymorphicIdentity(T t) {
260 template <typename... Ts>
261 struct VoidPolymorphic {
262 static void Run(Ts... t) {}
265 int Identity(int n) {
269 int ArrayGet(const int array[], int n) {
273 int Sum(int a, int b, int c, int d, int e, int f) {
274 return a + b + c + d + e + f;
277 const char* CStringIdentity(const char* s) {
281 int GetCopies(const CopyMoveCounter& counter) {
282 return counter.copies();
285 int UnwrapNoRefParent(NoRefParent p) {
289 int UnwrapNoRefParentPtr(NoRefParent* p) {
293 int UnwrapNoRefParentConstRef(const NoRefParent& p) {
297 void RefArgSet(int &n) {
301 void PtrArgSet(int *n) {
305 int FunctionWithWeakFirstParam(WeakPtr<NoRef> o, int n) {
309 int FunctionWithScopedRefptrFirstParam(const scoped_refptr<HasRef>& o, int n) {
313 void TakesACallback(const Closure& callback) {
317 int Noexcept() noexcept {
321 class BindTest : public ::testing::Test {
324 const_has_ref_ptr_ = &has_ref_;
325 const_no_ref_ptr_ = &no_ref_;
326 static_func_mock_ptr = &static_func_mock_;
329 ~BindTest() override = default;
331 static void VoidFunc0() {
332 static_func_mock_ptr->VoidMethod0();
335 static int IntFunc0() { return static_func_mock_ptr->IntMethod0(); }
336 int NoexceptMethod() noexcept { return 42; }
337 int ConstNoexceptMethod() const noexcept { return 42; }
340 StrictMock<NoRef> no_ref_;
341 StrictMock<HasRef> has_ref_;
342 const HasRef* const_has_ref_ptr_;
343 const NoRef* const_no_ref_ptr_;
344 StrictMock<NoRef> static_func_mock_;
346 // Used by the static functions to perform expectations.
347 static StrictMock<NoRef>* static_func_mock_ptr;
350 DISALLOW_COPY_AND_ASSIGN(BindTest);
353 StrictMock<NoRef>* BindTest::static_func_mock_ptr;
354 StrictMock<NoRef>* g_func_mock_ptr;
357 g_func_mock_ptr->VoidMethod0();
361 return g_func_mock_ptr->IntMethod0();
364 TEST_F(BindTest, BasicTest) {
365 Callback<int(int, int, int)> cb = Bind(&Sum, 32, 16, 8);
366 EXPECT_EQ(92, cb.Run(13, 12, 11));
368 Callback<int(int, int, int, int, int, int)> c1 = Bind(&Sum);
369 EXPECT_EQ(69, c1.Run(14, 13, 12, 11, 10, 9));
371 Callback<int(int, int, int)> c2 = Bind(c1, 32, 16, 8);
372 EXPECT_EQ(86, c2.Run(11, 10, 9));
374 Callback<int()> c3 = Bind(c2, 4, 2, 1);
375 EXPECT_EQ(63, c3.Run());
378 // Test that currying the rvalue result of another Bind() works correctly.
379 // - rvalue should be usable as argument to Bind().
380 // - multiple runs of resulting Callback remain valid.
381 TEST_F(BindTest, CurryingRvalueResultOfBind) {
383 RepeatingClosure cb = BindRepeating(&TakesACallback,
384 BindRepeating(&PtrArgSet, &n));
386 // If we implement Bind() such that the return value has auto_ptr-like
387 // semantics, the second call here will fail because ownership of
388 // the internal BindState<> would have been transfered to a *temporary*
389 // constructon of a Callback object on the first call.
398 TEST_F(BindTest, RepeatingCallbackBasicTest) {
399 RepeatingCallback<int(int)> c0 = BindRepeating(&Sum, 1, 2, 4, 8, 16);
401 // RepeatingCallback can run via a lvalue-reference.
402 EXPECT_EQ(63, c0.Run(32));
404 // It is valid to call a RepeatingCallback more than once.
405 EXPECT_EQ(54, c0.Run(23));
407 // BindRepeating can handle a RepeatingCallback as the target functor.
408 RepeatingCallback<int()> c1 = BindRepeating(c0, 11);
410 // RepeatingCallback can run via a rvalue-reference.
411 EXPECT_EQ(42, std::move(c1).Run());
413 // BindRepeating can handle a rvalue-reference of RepeatingCallback.
414 EXPECT_EQ(32, BindRepeating(std::move(c0), 1).Run());
417 TEST_F(BindTest, OnceCallbackBasicTest) {
418 OnceCallback<int(int)> c0 = BindOnce(&Sum, 1, 2, 4, 8, 16);
420 // OnceCallback can run via a rvalue-reference.
421 EXPECT_EQ(63, std::move(c0).Run(32));
423 // After running via the rvalue-reference, the value of the OnceCallback
424 // is undefined. The implementation simply clears the instance after the
426 EXPECT_TRUE(c0.is_null());
428 c0 = BindOnce(&Sum, 2, 3, 5, 7, 11);
430 // BindOnce can handle a rvalue-reference of OnceCallback as the target
432 OnceCallback<int()> c1 = BindOnce(std::move(c0), 13);
433 EXPECT_EQ(41, std::move(c1).Run());
435 RepeatingCallback<int(int)> c2 = BindRepeating(&Sum, 2, 3, 5, 7, 11);
436 EXPECT_EQ(41, BindOnce(c2, 13).Run());
439 // IgnoreResult adapter test.
440 // - Function with return value.
441 // - Method with return value.
442 // - Const Method with return.
443 // - Method with return value bound to WeakPtr<>.
444 // - Const Method with return bound to WeakPtr<>.
445 TEST_F(BindTest, IgnoreResultForRepeating) {
446 EXPECT_CALL(static_func_mock_, IntMethod0()).WillOnce(Return(1337));
447 EXPECT_CALL(has_ref_, AddRef()).Times(2);
448 EXPECT_CALL(has_ref_, Release()).Times(2);
449 EXPECT_CALL(has_ref_, HasAtLeastOneRef()).WillRepeatedly(Return(true));
450 EXPECT_CALL(has_ref_, IntMethod0()).WillOnce(Return(10));
451 EXPECT_CALL(has_ref_, IntConstMethod0()).WillOnce(Return(11));
452 EXPECT_CALL(no_ref_, IntMethod0()).WillOnce(Return(12));
453 EXPECT_CALL(no_ref_, IntConstMethod0()).WillOnce(Return(13));
455 RepeatingClosure normal_func_cb = BindRepeating(IgnoreResult(&IntFunc0));
456 normal_func_cb.Run();
458 RepeatingClosure non_void_method_cb =
459 BindRepeating(IgnoreResult(&HasRef::IntMethod0), &has_ref_);
460 non_void_method_cb.Run();
462 RepeatingClosure non_void_const_method_cb =
463 BindRepeating(IgnoreResult(&HasRef::IntConstMethod0), &has_ref_);
464 non_void_const_method_cb.Run();
466 WeakPtrFactory<NoRef> weak_factory(&no_ref_);
467 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_);
469 RepeatingClosure non_void_weak_method_cb =
470 BindRepeating(IgnoreResult(&NoRef::IntMethod0),
471 weak_factory.GetWeakPtr());
472 non_void_weak_method_cb.Run();
474 RepeatingClosure non_void_weak_const_method_cb =
475 BindRepeating(IgnoreResult(&NoRef::IntConstMethod0),
476 weak_factory.GetWeakPtr());
477 non_void_weak_const_method_cb.Run();
479 weak_factory.InvalidateWeakPtrs();
480 non_void_weak_const_method_cb.Run();
481 non_void_weak_method_cb.Run();
484 TEST_F(BindTest, IgnoreResultForOnce) {
485 EXPECT_CALL(static_func_mock_, IntMethod0()).WillOnce(Return(1337));
486 EXPECT_CALL(has_ref_, AddRef()).Times(2);
487 EXPECT_CALL(has_ref_, Release()).Times(2);
488 EXPECT_CALL(has_ref_, HasAtLeastOneRef()).WillRepeatedly(Return(true));
489 EXPECT_CALL(has_ref_, IntMethod0()).WillOnce(Return(10));
490 EXPECT_CALL(has_ref_, IntConstMethod0()).WillOnce(Return(11));
492 OnceClosure normal_func_cb = BindOnce(IgnoreResult(&IntFunc0));
493 std::move(normal_func_cb).Run();
495 OnceClosure non_void_method_cb =
496 BindOnce(IgnoreResult(&HasRef::IntMethod0), &has_ref_);
497 std::move(non_void_method_cb).Run();
499 OnceClosure non_void_const_method_cb =
500 BindOnce(IgnoreResult(&HasRef::IntConstMethod0), &has_ref_);
501 std::move(non_void_const_method_cb).Run();
503 WeakPtrFactory<NoRef> weak_factory(&no_ref_);
504 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_);
506 OnceClosure non_void_weak_method_cb =
507 BindOnce(IgnoreResult(&NoRef::IntMethod0),
508 weak_factory.GetWeakPtr());
509 OnceClosure non_void_weak_const_method_cb =
510 BindOnce(IgnoreResult(&NoRef::IntConstMethod0),
511 weak_factory.GetWeakPtr());
513 weak_factory.InvalidateWeakPtrs();
514 std::move(non_void_weak_const_method_cb).Run();
515 std::move(non_void_weak_method_cb).Run();
518 // Functions that take reference parameters.
519 // - Forced reference parameter type still stores a copy.
520 // - Forced const reference parameter type still stores a copy.
521 TEST_F(BindTest, ReferenceArgumentBindingForRepeating) {
524 const int& const_ref_n = n;
526 RepeatingCallback<int()> ref_copies_cb = BindRepeating(&Identity, ref_n);
527 EXPECT_EQ(n, ref_copies_cb.Run());
529 EXPECT_EQ(n - 1, ref_copies_cb.Run());
531 RepeatingCallback<int()> const_ref_copies_cb =
532 BindRepeating(&Identity, const_ref_n);
533 EXPECT_EQ(n, const_ref_copies_cb.Run());
535 EXPECT_EQ(n - 1, const_ref_copies_cb.Run());
538 TEST_F(BindTest, ReferenceArgumentBindingForOnce) {
541 const int& const_ref_n = n;
543 OnceCallback<int()> ref_copies_cb = BindOnce(&Identity, ref_n);
545 EXPECT_EQ(n - 1, std::move(ref_copies_cb).Run());
547 OnceCallback<int()> const_ref_copies_cb =
548 BindOnce(&Identity, const_ref_n);
550 EXPECT_EQ(n - 1, std::move(const_ref_copies_cb).Run());
553 // Check that we can pass in arrays and have them be stored as a pointer.
554 // - Array of values stores a pointer.
555 // - Array of const values stores a pointer.
556 TEST_F(BindTest, ArrayArgumentBindingForRepeating) {
557 int array[4] = {1, 1, 1, 1};
558 const int (*const_array_ptr)[4] = &array;
560 RepeatingCallback<int()> array_cb = BindRepeating(&ArrayGet, array, 1);
561 EXPECT_EQ(1, array_cb.Run());
563 RepeatingCallback<int()> const_array_cb =
564 BindRepeating(&ArrayGet, *const_array_ptr, 1);
565 EXPECT_EQ(1, const_array_cb.Run());
568 EXPECT_EQ(3, array_cb.Run());
569 EXPECT_EQ(3, const_array_cb.Run());
572 TEST_F(BindTest, ArrayArgumentBindingForOnce) {
573 int array[4] = {1, 1, 1, 1};
574 const int (*const_array_ptr)[4] = &array;
576 OnceCallback<int()> array_cb = BindOnce(&ArrayGet, array, 1);
577 OnceCallback<int()> const_array_cb =
578 BindOnce(&ArrayGet, *const_array_ptr, 1);
581 EXPECT_EQ(3, std::move(array_cb).Run());
582 EXPECT_EQ(3, std::move(const_array_cb).Run());
585 // WeakPtr() support.
586 // - Method bound to WeakPtr<> to non-const object.
587 // - Const method bound to WeakPtr<> to non-const object.
588 // - Const method bound to WeakPtr<> to const object.
589 // - Normal Function with WeakPtr<> as P1 can have return type and is
591 TEST_F(BindTest, WeakPtrForRepeating) {
592 EXPECT_CALL(no_ref_, VoidMethod0());
593 EXPECT_CALL(no_ref_, VoidConstMethod0()).Times(2);
595 WeakPtrFactory<NoRef> weak_factory(&no_ref_);
596 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_);
598 RepeatingClosure method_cb =
599 BindRepeating(&NoRef::VoidMethod0, weak_factory.GetWeakPtr());
602 RepeatingClosure const_method_cb =
603 BindRepeating(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr());
604 const_method_cb.Run();
606 RepeatingClosure const_method_const_ptr_cb =
607 BindRepeating(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr());
608 const_method_const_ptr_cb.Run();
610 RepeatingCallback<int(int)> normal_func_cb =
611 BindRepeating(&FunctionWithWeakFirstParam, weak_factory.GetWeakPtr());
612 EXPECT_EQ(1, normal_func_cb.Run(1));
614 weak_factory.InvalidateWeakPtrs();
615 const_weak_factory.InvalidateWeakPtrs();
618 const_method_cb.Run();
619 const_method_const_ptr_cb.Run();
621 // Still runs even after the pointers are invalidated.
622 EXPECT_EQ(2, normal_func_cb.Run(2));
625 TEST_F(BindTest, WeakPtrForOnce) {
626 WeakPtrFactory<NoRef> weak_factory(&no_ref_);
627 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_);
629 OnceClosure method_cb =
630 BindOnce(&NoRef::VoidMethod0, weak_factory.GetWeakPtr());
631 OnceClosure const_method_cb =
632 BindOnce(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr());
633 OnceClosure const_method_const_ptr_cb =
634 BindOnce(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr());
635 Callback<int(int)> normal_func_cb =
636 Bind(&FunctionWithWeakFirstParam, weak_factory.GetWeakPtr());
638 weak_factory.InvalidateWeakPtrs();
639 const_weak_factory.InvalidateWeakPtrs();
641 std::move(method_cb).Run();
642 std::move(const_method_cb).Run();
643 std::move(const_method_const_ptr_cb).Run();
645 // Still runs even after the pointers are invalidated.
646 EXPECT_EQ(2, std::move(normal_func_cb).Run(2));
649 // ConstRef() wrapper support.
650 // - Binding w/o ConstRef takes a copy.
651 // - Binding a ConstRef takes a reference.
652 // - Binding ConstRef to a function ConstRef does not copy on invoke.
653 TEST_F(BindTest, ConstRefForRepeating) {
656 RepeatingCallback<int()> copy_cb = BindRepeating(&Identity, n);
657 RepeatingCallback<int()> const_ref_cb = BindRepeating(&Identity, ConstRef(n));
658 EXPECT_EQ(n, copy_cb.Run());
659 EXPECT_EQ(n, const_ref_cb.Run());
661 EXPECT_EQ(n - 1, copy_cb.Run());
662 EXPECT_EQ(n, const_ref_cb.Run());
666 int move_constructs = 0;
667 int move_assigns = 0;
668 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns);
669 RepeatingCallback<int()> all_const_ref_cb =
670 BindRepeating(&GetCopies, ConstRef(counter));
671 EXPECT_EQ(0, all_const_ref_cb.Run());
672 EXPECT_EQ(0, copies);
673 EXPECT_EQ(0, assigns);
674 EXPECT_EQ(0, move_constructs);
675 EXPECT_EQ(0, move_assigns);
678 TEST_F(BindTest, ConstRefForOnce) {
681 OnceCallback<int()> copy_cb = BindOnce(&Identity, n);
682 OnceCallback<int()> const_ref_cb = BindOnce(&Identity, ConstRef(n));
684 EXPECT_EQ(n - 1, std::move(copy_cb).Run());
685 EXPECT_EQ(n, std::move(const_ref_cb).Run());
689 int move_constructs = 0;
690 int move_assigns = 0;
691 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns);
692 OnceCallback<int()> all_const_ref_cb =
693 BindOnce(&GetCopies, ConstRef(counter));
694 EXPECT_EQ(0, std::move(all_const_ref_cb).Run());
695 EXPECT_EQ(0, copies);
696 EXPECT_EQ(0, assigns);
697 EXPECT_EQ(0, move_constructs);
698 EXPECT_EQ(0, move_assigns);
701 // Test Owned() support.
702 TEST_F(BindTest, OwnedForRepeating) {
704 DeleteCounter* counter = new DeleteCounter(&deletes);
706 // If we don't capture, delete happens on Callback destruction/reset.
707 // return the same value.
708 RepeatingCallback<DeleteCounter*()> no_capture_cb =
709 BindRepeating(&PolymorphicIdentity<DeleteCounter*>, Owned(counter));
710 ASSERT_EQ(counter, no_capture_cb.Run());
711 ASSERT_EQ(counter, no_capture_cb.Run());
712 EXPECT_EQ(0, deletes);
713 no_capture_cb.Reset(); // This should trigger a delete.
714 EXPECT_EQ(1, deletes);
717 counter = new DeleteCounter(&deletes);
718 RepeatingClosure own_object_cb =
719 BindRepeating(&DeleteCounter::VoidMethod0, Owned(counter));
721 EXPECT_EQ(0, deletes);
722 own_object_cb.Reset();
723 EXPECT_EQ(1, deletes);
726 TEST_F(BindTest, OwnedForOnce) {
728 DeleteCounter* counter = new DeleteCounter(&deletes);
730 // If we don't capture, delete happens on Callback destruction/reset.
731 // return the same value.
732 OnceCallback<DeleteCounter*()> no_capture_cb =
733 BindOnce(&PolymorphicIdentity<DeleteCounter*>, Owned(counter));
734 EXPECT_EQ(0, deletes);
735 no_capture_cb.Reset(); // This should trigger a delete.
736 EXPECT_EQ(1, deletes);
739 counter = new DeleteCounter(&deletes);
740 OnceClosure own_object_cb =
741 BindOnce(&DeleteCounter::VoidMethod0, Owned(counter));
742 EXPECT_EQ(0, deletes);
743 own_object_cb.Reset();
744 EXPECT_EQ(1, deletes);
747 template <typename T>
748 class BindVariantsTest : public ::testing::Test {
751 struct RepeatingTestConfig {
752 template <typename Signature>
753 using CallbackType = RepeatingCallback<Signature>;
754 using ClosureType = RepeatingClosure;
756 template <typename F, typename... Args>
757 static CallbackType<MakeUnboundRunType<F, Args...>>
758 Bind(F&& f, Args&&... args) {
759 return BindRepeating(std::forward<F>(f), std::forward<Args>(args)...);
763 struct OnceTestConfig {
764 template <typename Signature>
765 using CallbackType = OnceCallback<Signature>;
766 using ClosureType = OnceClosure;
768 template <typename F, typename... Args>
769 static CallbackType<MakeUnboundRunType<F, Args...>>
770 Bind(F&& f, Args&&... args) {
771 return BindOnce(std::forward<F>(f), std::forward<Args>(args)...);
775 using BindVariantsTestConfig = ::testing::Types<
776 RepeatingTestConfig, OnceTestConfig>;
777 TYPED_TEST_CASE(BindVariantsTest, BindVariantsTestConfig);
779 template <typename TypeParam, typename Signature>
780 using CallbackType = typename TypeParam::template CallbackType<Signature>;
782 // Function type support.
783 // - Normal function.
784 // - Normal function bound with non-refcounted first argument.
785 // - Method bound to non-const object.
786 // - Method bound to scoped_refptr.
787 // - Const method bound to non-const object.
788 // - Const method bound to const object.
789 // - Derived classes can be used with pointers to non-virtual base functions.
790 // - Derived classes can be used with pointers to virtual base functions (and
791 // preserve virtual dispatch).
792 TYPED_TEST(BindVariantsTest, FunctionTypeSupport) {
793 using ClosureType = typename TypeParam::ClosureType;
795 StrictMock<HasRef> has_ref;
796 StrictMock<NoRef> no_ref;
797 StrictMock<NoRef> static_func_mock;
798 const HasRef* const_has_ref_ptr = &has_ref;
799 g_func_mock_ptr = &static_func_mock;
801 EXPECT_CALL(static_func_mock, VoidMethod0());
802 EXPECT_CALL(has_ref, AddRef()).Times(4);
803 EXPECT_CALL(has_ref, Release()).Times(4);
804 EXPECT_CALL(has_ref, HasAtLeastOneRef()).WillRepeatedly(Return(true));
805 EXPECT_CALL(has_ref, VoidMethod0()).Times(2);
806 EXPECT_CALL(has_ref, VoidConstMethod0()).Times(2);
808 ClosureType normal_cb = TypeParam::Bind(&VoidFunc0);
809 CallbackType<TypeParam, NoRef*()> normal_non_refcounted_cb =
810 TypeParam::Bind(&PolymorphicIdentity<NoRef*>, &no_ref);
811 std::move(normal_cb).Run();
812 EXPECT_EQ(&no_ref, std::move(normal_non_refcounted_cb).Run());
814 ClosureType method_cb = TypeParam::Bind(&HasRef::VoidMethod0, &has_ref);
815 ClosureType method_refptr_cb =
816 TypeParam::Bind(&HasRef::VoidMethod0, WrapRefCounted(&has_ref));
817 ClosureType const_method_nonconst_obj_cb =
818 TypeParam::Bind(&HasRef::VoidConstMethod0, &has_ref);
819 ClosureType const_method_const_obj_cb =
820 TypeParam::Bind(&HasRef::VoidConstMethod0, const_has_ref_ptr);
821 std::move(method_cb).Run();
822 std::move(method_refptr_cb).Run();
823 std::move(const_method_nonconst_obj_cb).Run();
824 std::move(const_method_const_obj_cb).Run();
828 ClosureType virtual_set_cb = TypeParam::Bind(&Parent::VirtualSet, &child);
829 std::move(virtual_set_cb).Run();
830 EXPECT_EQ(kChildValue, child.value);
833 ClosureType non_virtual_set_cb =
834 TypeParam::Bind(&Parent::NonVirtualSet, &child);
835 std::move(non_virtual_set_cb).Run();
836 EXPECT_EQ(kParentValue, child.value);
839 // Return value support.
840 // - Function with return value.
841 // - Method with return value.
842 // - Const method with return value.
843 // - Move-only return value.
844 TYPED_TEST(BindVariantsTest, ReturnValues) {
845 StrictMock<NoRef> static_func_mock;
846 StrictMock<HasRef> has_ref;
847 g_func_mock_ptr = &static_func_mock;
848 const HasRef* const_has_ref_ptr = &has_ref;
850 EXPECT_CALL(static_func_mock, IntMethod0()).WillOnce(Return(1337));
851 EXPECT_CALL(has_ref, AddRef()).Times(4);
852 EXPECT_CALL(has_ref, Release()).Times(4);
853 EXPECT_CALL(has_ref, HasAtLeastOneRef()).WillRepeatedly(Return(true));
854 EXPECT_CALL(has_ref, IntMethod0()).WillOnce(Return(31337));
855 EXPECT_CALL(has_ref, IntConstMethod0())
856 .WillOnce(Return(41337))
857 .WillOnce(Return(51337));
858 EXPECT_CALL(has_ref, UniquePtrMethod0())
859 .WillOnce(Return(ByMove(std::make_unique<int>(42))));
861 CallbackType<TypeParam, int()> normal_cb = TypeParam::Bind(&IntFunc0);
862 CallbackType<TypeParam, int()> method_cb =
863 TypeParam::Bind(&HasRef::IntMethod0, &has_ref);
864 CallbackType<TypeParam, int()> const_method_nonconst_obj_cb =
865 TypeParam::Bind(&HasRef::IntConstMethod0, &has_ref);
866 CallbackType<TypeParam, int()> const_method_const_obj_cb =
867 TypeParam::Bind(&HasRef::IntConstMethod0, const_has_ref_ptr);
868 CallbackType<TypeParam, std::unique_ptr<int>()> move_only_rv_cb =
869 TypeParam::Bind(&HasRef::UniquePtrMethod0, &has_ref);
870 EXPECT_EQ(1337, std::move(normal_cb).Run());
871 EXPECT_EQ(31337, std::move(method_cb).Run());
872 EXPECT_EQ(41337, std::move(const_method_nonconst_obj_cb).Run());
873 EXPECT_EQ(51337, std::move(const_method_const_obj_cb).Run());
874 EXPECT_EQ(42, *std::move(move_only_rv_cb).Run());
877 // Argument binding tests.
878 // - Argument binding to primitive.
879 // - Argument binding to primitive pointer.
880 // - Argument binding to a literal integer.
881 // - Argument binding to a literal string.
882 // - Argument binding with template function.
883 // - Argument binding to an object.
884 // - Argument binding to pointer to incomplete type.
885 // - Argument gets type converted.
886 // - Pointer argument gets converted.
887 // - Const Reference forces conversion.
888 TYPED_TEST(BindVariantsTest, ArgumentBinding) {
891 EXPECT_EQ(n, TypeParam::Bind(&Identity, n).Run());
892 EXPECT_EQ(&n, TypeParam::Bind(&PolymorphicIdentity<int*>, &n).Run());
893 EXPECT_EQ(3, TypeParam::Bind(&Identity, 3).Run());
894 EXPECT_STREQ("hi", TypeParam::Bind(&CStringIdentity, "hi").Run());
895 EXPECT_EQ(4, TypeParam::Bind(&PolymorphicIdentity<int>, 4).Run());
899 EXPECT_EQ(5, TypeParam::Bind(&UnwrapNoRefParent, p).Run());
901 IncompleteType* incomplete_ptr = reinterpret_cast<IncompleteType*>(123);
902 EXPECT_EQ(incomplete_ptr,
903 TypeParam::Bind(&PolymorphicIdentity<IncompleteType*>,
904 incomplete_ptr).Run());
908 EXPECT_EQ(6, TypeParam::Bind(&UnwrapNoRefParent, c).Run());
911 EXPECT_EQ(7, TypeParam::Bind(&UnwrapNoRefParentPtr, &c).Run());
914 EXPECT_EQ(8, TypeParam::Bind(&UnwrapNoRefParentConstRef, c).Run());
917 // Unbound argument type support tests.
919 // - Unbound pointer.
920 // - Unbound reference.
921 // - Unbound const reference.
922 // - Unbound unsized array.
923 // - Unbound sized array.
924 // - Unbound array-of-arrays.
925 TYPED_TEST(BindVariantsTest, UnboundArgumentTypeSupport) {
926 CallbackType<TypeParam, void(int)> unbound_value_cb =
927 TypeParam::Bind(&VoidPolymorphic<int>::Run);
928 CallbackType<TypeParam, void(int*)> unbound_pointer_cb =
929 TypeParam::Bind(&VoidPolymorphic<int*>::Run);
930 CallbackType<TypeParam, void(int&)> unbound_ref_cb =
931 TypeParam::Bind(&VoidPolymorphic<int&>::Run);
932 CallbackType<TypeParam, void(const int&)> unbound_const_ref_cb =
933 TypeParam::Bind(&VoidPolymorphic<const int&>::Run);
934 CallbackType<TypeParam, void(int[])> unbound_unsized_array_cb =
935 TypeParam::Bind(&VoidPolymorphic<int[]>::Run);
936 CallbackType<TypeParam, void(int[2])> unbound_sized_array_cb =
937 TypeParam::Bind(&VoidPolymorphic<int[2]>::Run);
938 CallbackType<TypeParam, void(int[][2])> unbound_array_of_arrays_cb =
939 TypeParam::Bind(&VoidPolymorphic<int[][2]>::Run);
940 CallbackType<TypeParam, void(int&)> unbound_ref_with_bound_arg =
941 TypeParam::Bind(&VoidPolymorphic<int, int&>::Run, 1);
944 // Function with unbound reference parameter.
945 // - Original parameter is modified by callback.
946 TYPED_TEST(BindVariantsTest, UnboundReferenceSupport) {
948 CallbackType<TypeParam, void(int&)> unbound_ref_cb =
949 TypeParam::Bind(&RefArgSet);
950 std::move(unbound_ref_cb).Run(n);
954 // Unretained() wrapper support.
955 // - Method bound to Unretained() non-const object.
956 // - Const method bound to Unretained() non-const object.
957 // - Const method bound to Unretained() const object.
958 TYPED_TEST(BindVariantsTest, Unretained) {
959 StrictMock<NoRef> no_ref;
960 const NoRef* const_no_ref_ptr = &no_ref;
962 EXPECT_CALL(no_ref, VoidMethod0());
963 EXPECT_CALL(no_ref, VoidConstMethod0()).Times(2);
965 TypeParam::Bind(&NoRef::VoidMethod0, Unretained(&no_ref)).Run();
966 TypeParam::Bind(&NoRef::VoidConstMethod0, Unretained(&no_ref)).Run();
967 TypeParam::Bind(&NoRef::VoidConstMethod0, Unretained(const_no_ref_ptr)).Run();
970 TYPED_TEST(BindVariantsTest, ScopedRefptr) {
971 StrictMock<HasRef> has_ref;
972 EXPECT_CALL(has_ref, AddRef()).Times(1);
973 EXPECT_CALL(has_ref, Release()).Times(1);
974 EXPECT_CALL(has_ref, HasAtLeastOneRef()).WillRepeatedly(Return(true));
976 const scoped_refptr<HasRef> refptr(&has_ref);
977 CallbackType<TypeParam, int()> scoped_refptr_const_ref_cb =
978 TypeParam::Bind(&FunctionWithScopedRefptrFirstParam,
979 base::ConstRef(refptr), 1);
980 EXPECT_EQ(1, std::move(scoped_refptr_const_ref_cb).Run());
983 TYPED_TEST(BindVariantsTest, UniquePtrReceiver) {
984 std::unique_ptr<StrictMock<NoRef>> no_ref(new StrictMock<NoRef>);
985 EXPECT_CALL(*no_ref, VoidMethod0()).Times(1);
986 TypeParam::Bind(&NoRef::VoidMethod0, std::move(no_ref)).Run();
989 // Tests for Passed() wrapper support:
990 // - Passed() can be constructed from a pointer to scoper.
991 // - Passed() can be constructed from a scoper rvalue.
992 // - Using Passed() gives Callback Ownership.
993 // - Ownership is transferred from Callback to callee on the first Run().
994 // - Callback supports unbound arguments.
995 template <typename T>
996 class BindMoveOnlyTypeTest : public ::testing::Test {
999 struct CustomDeleter {
1000 void operator()(DeleteCounter* c) { delete c; }
1003 using MoveOnlyTypesToTest =
1004 ::testing::Types<std::unique_ptr<DeleteCounter>,
1005 std::unique_ptr<DeleteCounter, CustomDeleter>>;
1006 TYPED_TEST_CASE(BindMoveOnlyTypeTest, MoveOnlyTypesToTest);
1008 TYPED_TEST(BindMoveOnlyTypeTest, PassedToBoundCallback) {
1011 TypeParam ptr(new DeleteCounter(&deletes));
1012 Callback<TypeParam()> callback = Bind(&PassThru<TypeParam>, Passed(&ptr));
1013 EXPECT_FALSE(ptr.get());
1014 EXPECT_EQ(0, deletes);
1016 // If we never invoke the Callback, it retains ownership and deletes.
1018 EXPECT_EQ(1, deletes);
1021 TYPED_TEST(BindMoveOnlyTypeTest, PassedWithRvalue) {
1023 Callback<TypeParam()> callback = Bind(
1024 &PassThru<TypeParam>, Passed(TypeParam(new DeleteCounter(&deletes))));
1025 EXPECT_EQ(0, deletes);
1027 // If we never invoke the Callback, it retains ownership and deletes.
1029 EXPECT_EQ(1, deletes);
1032 // Check that ownership can be transferred back out.
1033 TYPED_TEST(BindMoveOnlyTypeTest, ReturnMoveOnlyType) {
1035 DeleteCounter* counter = new DeleteCounter(&deletes);
1036 Callback<TypeParam()> callback =
1037 Bind(&PassThru<TypeParam>, Passed(TypeParam(counter)));
1038 TypeParam result = callback.Run();
1039 ASSERT_EQ(counter, result.get());
1040 EXPECT_EQ(0, deletes);
1042 // Resetting does not delete since ownership was transferred.
1044 EXPECT_EQ(0, deletes);
1046 // Ensure that we actually did get ownership.
1048 EXPECT_EQ(1, deletes);
1051 TYPED_TEST(BindMoveOnlyTypeTest, UnboundForwarding) {
1053 TypeParam ptr(new DeleteCounter(&deletes));
1054 // Test unbound argument forwarding.
1055 Callback<TypeParam(TypeParam)> cb_unbound = Bind(&PassThru<TypeParam>);
1056 cb_unbound.Run(std::move(ptr));
1057 EXPECT_EQ(1, deletes);
1060 void VerifyVector(const std::vector<std::unique_ptr<int>>& v) {
1061 ASSERT_EQ(1u, v.size());
1062 EXPECT_EQ(12345, *v[0]);
1065 std::vector<std::unique_ptr<int>> AcceptAndReturnMoveOnlyVector(
1066 std::vector<std::unique_ptr<int>> v) {
1071 // Test that a vector containing move-only types can be used with Callback.
1072 TEST_F(BindTest, BindMoveOnlyVector) {
1073 using MoveOnlyVector = std::vector<std::unique_ptr<int>>;
1076 v.push_back(std::make_unique<int>(12345));
1078 // Early binding should work:
1079 base::Callback<MoveOnlyVector()> bound_cb =
1080 base::Bind(&AcceptAndReturnMoveOnlyVector, Passed(&v));
1081 MoveOnlyVector intermediate_result = bound_cb.Run();
1082 VerifyVector(intermediate_result);
1084 // As should passing it as an argument to Run():
1085 base::Callback<MoveOnlyVector(MoveOnlyVector)> unbound_cb =
1086 base::Bind(&AcceptAndReturnMoveOnlyVector);
1087 MoveOnlyVector final_result = unbound_cb.Run(std::move(intermediate_result));
1088 VerifyVector(final_result);
1091 // Argument copy-constructor usage for non-reference copy-only parameters.
1092 // - Bound arguments are only copied once.
1093 // - Forwarded arguments are only copied once.
1094 // - Forwarded arguments with coercions are only copied twice (once for the
1095 // coercion, and one for the final dispatch).
1096 TEST_F(BindTest, ArgumentCopies) {
1100 CopyCounter counter(&copies, &assigns);
1101 Bind(&VoidPolymorphic<CopyCounter>::Run, counter);
1102 EXPECT_EQ(1, copies);
1103 EXPECT_EQ(0, assigns);
1107 Bind(&VoidPolymorphic<CopyCounter>::Run, CopyCounter(&copies, &assigns));
1108 EXPECT_EQ(1, copies);
1109 EXPECT_EQ(0, assigns);
1113 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(counter);
1114 EXPECT_EQ(2, copies);
1115 EXPECT_EQ(0, assigns);
1119 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(CopyCounter(&copies, &assigns));
1120 EXPECT_EQ(1, copies);
1121 EXPECT_EQ(0, assigns);
1125 DerivedCopyMoveCounter derived(&copies, &assigns, nullptr, nullptr);
1126 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(CopyCounter(derived));
1127 EXPECT_EQ(2, copies);
1128 EXPECT_EQ(0, assigns);
1132 Bind(&VoidPolymorphic<CopyCounter>::Run)
1134 DerivedCopyMoveCounter(&copies, &assigns, nullptr, nullptr)));
1135 EXPECT_EQ(2, copies);
1136 EXPECT_EQ(0, assigns);
1139 // Argument move-constructor usage for move-only parameters.
1140 // - Bound arguments passed by move are not copied.
1141 TEST_F(BindTest, ArgumentMoves) {
1142 int move_constructs = 0;
1143 int move_assigns = 0;
1145 Bind(&VoidPolymorphic<const MoveCounter&>::Run,
1146 MoveCounter(&move_constructs, &move_assigns));
1147 EXPECT_EQ(1, move_constructs);
1148 EXPECT_EQ(0, move_assigns);
1150 // TODO(tzik): Support binding move-only type into a non-reference parameter
1151 // of a variant of Callback.
1153 move_constructs = 0;
1155 Bind(&VoidPolymorphic<MoveCounter>::Run)
1156 .Run(MoveCounter(&move_constructs, &move_assigns));
1157 EXPECT_EQ(1, move_constructs);
1158 EXPECT_EQ(0, move_assigns);
1160 move_constructs = 0;
1162 Bind(&VoidPolymorphic<MoveCounter>::Run)
1163 .Run(MoveCounter(DerivedCopyMoveCounter(
1164 nullptr, nullptr, &move_constructs, &move_assigns)));
1165 EXPECT_EQ(2, move_constructs);
1166 EXPECT_EQ(0, move_assigns);
1169 // Argument constructor usage for non-reference movable-copyable
1171 // - Bound arguments passed by move are not copied.
1172 // - Forwarded arguments are only copied once.
1173 // - Forwarded arguments with coercions are only copied once and moved once.
1174 TEST_F(BindTest, ArgumentCopiesAndMoves) {
1177 int move_constructs = 0;
1178 int move_assigns = 0;
1180 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns);
1181 Bind(&VoidPolymorphic<CopyMoveCounter>::Run, counter);
1182 EXPECT_EQ(1, copies);
1183 EXPECT_EQ(0, assigns);
1184 EXPECT_EQ(0, move_constructs);
1185 EXPECT_EQ(0, move_assigns);
1189 move_constructs = 0;
1191 Bind(&VoidPolymorphic<CopyMoveCounter>::Run,
1192 CopyMoveCounter(&copies, &assigns, &move_constructs, &move_assigns));
1193 EXPECT_EQ(0, copies);
1194 EXPECT_EQ(0, assigns);
1195 EXPECT_EQ(1, move_constructs);
1196 EXPECT_EQ(0, move_assigns);
1200 move_constructs = 0;
1202 Bind(&VoidPolymorphic<CopyMoveCounter>::Run).Run(counter);
1203 EXPECT_EQ(1, copies);
1204 EXPECT_EQ(0, assigns);
1205 EXPECT_EQ(1, move_constructs);
1206 EXPECT_EQ(0, move_assigns);
1210 move_constructs = 0;
1212 Bind(&VoidPolymorphic<CopyMoveCounter>::Run)
1213 .Run(CopyMoveCounter(&copies, &assigns, &move_constructs, &move_assigns));
1214 EXPECT_EQ(0, copies);
1215 EXPECT_EQ(0, assigns);
1216 EXPECT_EQ(1, move_constructs);
1217 EXPECT_EQ(0, move_assigns);
1219 DerivedCopyMoveCounter derived_counter(&copies, &assigns, &move_constructs,
1223 move_constructs = 0;
1225 Bind(&VoidPolymorphic<CopyMoveCounter>::Run)
1226 .Run(CopyMoveCounter(derived_counter));
1227 EXPECT_EQ(1, copies);
1228 EXPECT_EQ(0, assigns);
1229 EXPECT_EQ(1, move_constructs);
1230 EXPECT_EQ(0, move_assigns);
1234 move_constructs = 0;
1236 Bind(&VoidPolymorphic<CopyMoveCounter>::Run)
1237 .Run(CopyMoveCounter(DerivedCopyMoveCounter(
1238 &copies, &assigns, &move_constructs, &move_assigns)));
1239 EXPECT_EQ(0, copies);
1240 EXPECT_EQ(0, assigns);
1241 EXPECT_EQ(2, move_constructs);
1242 EXPECT_EQ(0, move_assigns);
1245 TEST_F(BindTest, CapturelessLambda) {
1246 EXPECT_FALSE(internal::IsCallableObject<void>::value);
1247 EXPECT_FALSE(internal::IsCallableObject<int>::value);
1248 EXPECT_FALSE(internal::IsCallableObject<void (*)()>::value);
1249 EXPECT_FALSE(internal::IsCallableObject<void (NoRef::*)()>::value);
1252 EXPECT_TRUE(internal::IsCallableObject<decltype(f)>::value);
1255 auto g = [i]() { (void)i; };
1256 EXPECT_TRUE(internal::IsCallableObject<decltype(g)>::value);
1258 auto h = [](int, double) { return 'k'; };
1259 EXPECT_TRUE((std::is_same<
1261 internal::ExtractCallableRunType<decltype(h)>>::value));
1263 EXPECT_EQ(42, Bind([] { return 42; }).Run());
1264 EXPECT_EQ(42, Bind([](int i) { return i * 7; }, 6).Run());
1267 base::Callback<void(int)> cb =
1268 Bind([](int* x, int i) { *x *= i; }, Unretained(&x));
1275 TEST_F(BindTest, EmptyFunctor) {
1276 struct NonEmptyFunctor {
1277 int operator()() const { return x; }
1281 struct EmptyFunctor {
1282 int operator()() { return 42; }
1285 struct EmptyFunctorConst {
1286 int operator()() const { return 42; }
1289 EXPECT_TRUE(internal::IsCallableObject<NonEmptyFunctor>::value);
1290 EXPECT_TRUE(internal::IsCallableObject<EmptyFunctor>::value);
1291 EXPECT_TRUE(internal::IsCallableObject<EmptyFunctorConst>::value);
1292 EXPECT_EQ(42, BindOnce(EmptyFunctor()).Run());
1293 EXPECT_EQ(42, BindOnce(EmptyFunctorConst()).Run());
1294 EXPECT_EQ(42, BindRepeating(EmptyFunctorConst()).Run());
1297 TEST_F(BindTest, CapturingLambdaForTesting) {
1299 EXPECT_EQ(42, BindLambdaForTesting([=](int y) { return x * y; }).Run(7));
1301 auto f = [x](std::unique_ptr<int> y) { return x * *y; };
1302 EXPECT_EQ(42, BindLambdaForTesting(f).Run(std::make_unique<int>(7)));
1305 TEST_F(BindTest, Cancellation) {
1306 EXPECT_CALL(no_ref_, VoidMethodWithIntArg(_)).Times(2);
1308 WeakPtrFactory<NoRef> weak_factory(&no_ref_);
1309 RepeatingCallback<void(int)> cb =
1310 BindRepeating(&NoRef::VoidMethodWithIntArg, weak_factory.GetWeakPtr());
1311 RepeatingClosure cb2 = BindRepeating(cb, 8);
1312 OnceClosure cb3 = BindOnce(cb, 8);
1314 OnceCallback<void(int)> cb4 =
1315 BindOnce(&NoRef::VoidMethodWithIntArg, weak_factory.GetWeakPtr());
1316 EXPECT_FALSE(cb4.IsCancelled());
1318 OnceClosure cb5 = BindOnce(std::move(cb4), 8);
1320 EXPECT_FALSE(cb.IsCancelled());
1321 EXPECT_FALSE(cb2.IsCancelled());
1322 EXPECT_FALSE(cb3.IsCancelled());
1323 EXPECT_FALSE(cb5.IsCancelled());
1328 weak_factory.InvalidateWeakPtrs();
1330 EXPECT_TRUE(cb.IsCancelled());
1331 EXPECT_TRUE(cb2.IsCancelled());
1332 EXPECT_TRUE(cb3.IsCancelled());
1333 EXPECT_TRUE(cb5.IsCancelled());
1337 std::move(cb3).Run();
1338 std::move(cb5).Run();
1341 TEST_F(BindTest, OnceCallback) {
1342 // Check if Callback variants have declarations of conversions as expected.
1343 // Copy constructor and assignment of RepeatingCallback.
1344 static_assert(std::is_constructible<
1345 RepeatingClosure, const RepeatingClosure&>::value,
1346 "RepeatingClosure should be copyable.");
1348 std::is_assignable<RepeatingClosure, const RepeatingClosure&>::value,
1349 "RepeatingClosure should be copy-assignable.");
1351 // Move constructor and assignment of RepeatingCallback.
1352 static_assert(std::is_constructible<
1353 RepeatingClosure, RepeatingClosure&&>::value,
1354 "RepeatingClosure should be movable.");
1355 static_assert(std::is_assignable<RepeatingClosure, RepeatingClosure&&>::value,
1356 "RepeatingClosure should be move-assignable");
1358 // Conversions from OnceCallback to RepeatingCallback.
1359 static_assert(!std::is_constructible<
1360 RepeatingClosure, const OnceClosure&>::value,
1361 "OnceClosure should not be convertible to RepeatingClosure.");
1363 !std::is_assignable<RepeatingClosure, const OnceClosure&>::value,
1364 "OnceClosure should not be convertible to RepeatingClosure.");
1366 // Destructive conversions from OnceCallback to RepeatingCallback.
1367 static_assert(!std::is_constructible<
1368 RepeatingClosure, OnceClosure&&>::value,
1369 "OnceClosure should not be convertible to RepeatingClosure.");
1370 static_assert(!std::is_assignable<RepeatingClosure, OnceClosure&&>::value,
1371 "OnceClosure should not be convertible to RepeatingClosure.");
1373 // Copy constructor and assignment of OnceCallback.
1374 static_assert(!std::is_constructible<
1375 OnceClosure, const OnceClosure&>::value,
1376 "OnceClosure should not be copyable.");
1377 static_assert(!std::is_assignable<OnceClosure, const OnceClosure&>::value,
1378 "OnceClosure should not be copy-assignable");
1380 // Move constructor and assignment of OnceCallback.
1381 static_assert(std::is_constructible<
1382 OnceClosure, OnceClosure&&>::value,
1383 "OnceClosure should be movable.");
1384 static_assert(std::is_assignable<OnceClosure, OnceClosure&&>::value,
1385 "OnceClosure should be move-assignable.");
1387 // Conversions from RepeatingCallback to OnceCallback.
1388 static_assert(std::is_constructible<
1389 OnceClosure, const RepeatingClosure&>::value,
1390 "RepeatingClosure should be convertible to OnceClosure.");
1391 static_assert(std::is_assignable<OnceClosure, const RepeatingClosure&>::value,
1392 "RepeatingClosure should be convertible to OnceClosure.");
1394 // Destructive conversions from RepeatingCallback to OnceCallback.
1395 static_assert(std::is_constructible<
1396 OnceClosure, RepeatingClosure&&>::value,
1397 "RepeatingClosure should be convertible to OnceClosure.");
1398 static_assert(std::is_assignable<OnceClosure, RepeatingClosure&&>::value,
1399 "RepeatingClosure should be covretible to OnceClosure.");
1401 OnceClosure cb = BindOnce(&VoidPolymorphic<>::Run);
1402 std::move(cb).Run();
1404 // RepeatingCallback should be convertible to OnceCallback.
1405 OnceClosure cb2 = BindRepeating(&VoidPolymorphic<>::Run);
1406 std::move(cb2).Run();
1408 RepeatingClosure cb3 = BindRepeating(&VoidPolymorphic<>::Run);
1410 std::move(cb).Run();
1412 cb = std::move(cb2);
1414 OnceCallback<void(int)> cb4 =
1415 BindOnce(&VoidPolymorphic<std::unique_ptr<int>, int>::Run,
1416 std::make_unique<int>(0));
1417 BindOnce(std::move(cb4), 1).Run();
1420 // Callback construction and assignment tests.
1421 // - Construction from an InvokerStorageHolder should not cause ref/deref.
1422 // - Assignment from other callback should only cause one ref
1424 // TODO(ajwong): Is there actually a way to test this?
1427 int __fastcall FastCallFunc(int n) {
1431 int __stdcall StdCallFunc(int n) {
1435 // Windows specific calling convention support.
1436 // - Can bind a __fastcall function.
1437 // - Can bind a __stdcall function.
1438 TEST_F(BindTest, WindowsCallingConventions) {
1439 Callback<int()> fastcall_cb = Bind(&FastCallFunc, 1);
1440 EXPECT_EQ(1, fastcall_cb.Run());
1442 Callback<int()> stdcall_cb = Bind(&StdCallFunc, 2);
1443 EXPECT_EQ(2, stdcall_cb.Run());
1447 // Test unwrapping the various wrapping functions.
1449 TEST_F(BindTest, UnwrapUnretained) {
1451 auto unretained = Unretained(&i);
1452 EXPECT_EQ(&i, internal::Unwrap(unretained));
1453 EXPECT_EQ(&i, internal::Unwrap(std::move(unretained)));
1456 TEST_F(BindTest, UnwrapConstRef) {
1458 auto const_ref = ConstRef(p);
1459 EXPECT_EQ(&p, &internal::Unwrap(const_ref));
1460 EXPECT_EQ(&p, &internal::Unwrap(std::move(const_ref)));
1463 TEST_F(BindTest, UnwrapRetainedRef) {
1464 auto p = MakeRefCounted<RefCountedData<int>>();
1465 auto retained_ref = RetainedRef(p);
1466 EXPECT_EQ(p.get(), internal::Unwrap(retained_ref));
1467 EXPECT_EQ(p.get(), internal::Unwrap(std::move(retained_ref)));
1470 TEST_F(BindTest, UnwrapOwned) {
1472 auto owned = Owned(p);
1473 EXPECT_EQ(p, internal::Unwrap(owned));
1474 EXPECT_EQ(p, internal::Unwrap(std::move(owned)));
1477 TEST_F(BindTest, UnwrapPassed) {
1479 auto passed = Passed(WrapUnique(p));
1480 EXPECT_EQ(p, internal::Unwrap(passed).get());
1483 EXPECT_EQ(p, internal::Unwrap(Passed(WrapUnique(p))).get());
1486 TEST_F(BindTest, BindNoexcept) {
1487 EXPECT_EQ(42, base::BindOnce(&Noexcept).Run());
1490 base::BindOnce(&BindTest::NoexceptMethod, base::Unretained(this)).Run());
1492 42, base::BindOnce(&BindTest::ConstNoexceptMethod, base::Unretained(this))
1496 // Test null callbacks cause a DCHECK.
1497 TEST(BindDeathTest, NullCallback) {
1498 base::Callback<void(int)> null_cb;
1499 ASSERT_TRUE(null_cb.is_null());
1500 EXPECT_DCHECK_DEATH(base::Bind(null_cb, 42));
1503 TEST(BindDeathTest, BanFirstOwnerOfRefCountedType) {
1504 StrictMock<HasRef> has_ref;
1505 EXPECT_DCHECK_DEATH({
1506 EXPECT_CALL(has_ref, HasAtLeastOneRef()).WillOnce(Return(false));
1507 base::BindOnce(&HasRef::VoidMethod0, &has_ref);