OLD | NEW |
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "base/bind.h" | 5 #include "base/bind.h" |
6 | 6 |
7 #include "base/callback.h" | 7 #include "base/callback.h" |
| 8 #include "base/memory/ref_counted.h" |
| 9 #include "base/memory/scoped_ptr.h" |
| 10 #include "base/memory/weak_ptr.h" |
8 #include "testing/gmock/include/gmock/gmock.h" | 11 #include "testing/gmock/include/gmock/gmock.h" |
9 #include "testing/gtest/include/gtest/gtest.h" | 12 #include "testing/gtest/include/gtest/gtest.h" |
10 | 13 |
11 using ::testing::Mock; | 14 using ::testing::Mock; |
12 using ::testing::Return; | 15 using ::testing::Return; |
13 using ::testing::StrictMock; | 16 using ::testing::StrictMock; |
14 | 17 |
15 namespace base { | 18 namespace base { |
16 namespace { | 19 namespace { |
17 | 20 |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
95 CopyCounter(int* copies, int* assigns) | 98 CopyCounter(int* copies, int* assigns) |
96 : copies_(copies), assigns_(assigns) { | 99 : copies_(copies), assigns_(assigns) { |
97 } | 100 } |
98 | 101 |
99 CopyCounter(const CopyCounter& other) | 102 CopyCounter(const CopyCounter& other) |
100 : copies_(other.copies_), | 103 : copies_(other.copies_), |
101 assigns_(other.assigns_) { | 104 assigns_(other.assigns_) { |
102 (*copies_)++; | 105 (*copies_)++; |
103 } | 106 } |
104 | 107 |
105 // Probing for copies from coerscion. | 108 // Probing for copies from coercion. |
106 CopyCounter(const DerivedCopyCounter& other) | 109 CopyCounter(const DerivedCopyCounter& other) |
107 : copies_(other.copies_), | 110 : copies_(other.copies_), |
108 assigns_(other.assigns_) { | 111 assigns_(other.assigns_) { |
109 (*copies_)++; | 112 (*copies_)++; |
110 } | 113 } |
111 | 114 |
112 const CopyCounter& operator=(const CopyCounter& rhs) { | 115 const CopyCounter& operator=(const CopyCounter& rhs) { |
113 copies_ = rhs.copies_; | 116 copies_ = rhs.copies_; |
114 assigns_ = rhs.assigns_; | 117 assigns_ = rhs.assigns_; |
115 | 118 |
(...skipping 26 matching lines...) Expand all Loading... |
142 ~DeleteCounter() { | 145 ~DeleteCounter() { |
143 (*deletes_)++; | 146 (*deletes_)++; |
144 } | 147 } |
145 | 148 |
146 void VoidMethod0() {} | 149 void VoidMethod0() {} |
147 | 150 |
148 private: | 151 private: |
149 int* deletes_; | 152 int* deletes_; |
150 }; | 153 }; |
151 | 154 |
| 155 template <typename T> |
| 156 T PassThru(T scoper) { |
| 157 return scoper.Pass(); |
| 158 } |
| 159 |
152 // Some test functions that we can Bind to. | 160 // Some test functions that we can Bind to. |
153 template <typename T> | 161 template <typename T> |
154 T PolymorphicIdentity(T t) { | 162 T PolymorphicIdentity(T t) { |
155 return t; | 163 return t; |
156 } | 164 } |
157 | 165 |
158 template <typename T> | 166 template <typename T> |
159 void VoidPolymorphic1(T t) { | 167 void VoidPolymorphic1(T t) { |
160 } | 168 } |
161 | 169 |
(...skipping 499 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
661 | 669 |
662 // Test Owned() support. | 670 // Test Owned() support. |
663 TEST_F(BindTest, Owned) { | 671 TEST_F(BindTest, Owned) { |
664 int deletes = 0; | 672 int deletes = 0; |
665 DeleteCounter* counter = new DeleteCounter(&deletes); | 673 DeleteCounter* counter = new DeleteCounter(&deletes); |
666 | 674 |
667 // If we don't capture, delete happens on Callback destruction/reset. | 675 // If we don't capture, delete happens on Callback destruction/reset. |
668 // return the same value. | 676 // return the same value. |
669 Callback<DeleteCounter*(void)> no_capture_cb = | 677 Callback<DeleteCounter*(void)> no_capture_cb = |
670 Bind(&PolymorphicIdentity<DeleteCounter*>, Owned(counter)); | 678 Bind(&PolymorphicIdentity<DeleteCounter*>, Owned(counter)); |
671 EXPECT_EQ(counter, no_capture_cb.Run()); | 679 ASSERT_EQ(counter, no_capture_cb.Run()); |
672 EXPECT_EQ(counter, no_capture_cb.Run()); | 680 ASSERT_EQ(counter, no_capture_cb.Run()); |
673 EXPECT_EQ(0, deletes); | 681 EXPECT_EQ(0, deletes); |
674 no_capture_cb.Reset(); // This should trigger a delete. | 682 no_capture_cb.Reset(); // This should trigger a delete. |
675 EXPECT_EQ(1, deletes); | 683 EXPECT_EQ(1, deletes); |
676 | 684 |
677 deletes = 0; | 685 deletes = 0; |
678 counter = new DeleteCounter(&deletes); | 686 counter = new DeleteCounter(&deletes); |
679 base::Closure own_object_cb = | 687 base::Closure own_object_cb = |
680 Bind(&DeleteCounter::VoidMethod0, Owned(counter)); | 688 Bind(&DeleteCounter::VoidMethod0, Owned(counter)); |
681 own_object_cb.Run(); | 689 own_object_cb.Run(); |
682 EXPECT_EQ(0, deletes); | 690 EXPECT_EQ(0, deletes); |
683 own_object_cb.Reset(); | 691 own_object_cb.Reset(); |
684 EXPECT_EQ(1, deletes); | 692 EXPECT_EQ(1, deletes); |
685 } | 693 } |
686 | 694 |
| 695 // Passed() wrapper support. |
| 696 // - Passed() can be constructed from a pointer to scoper. |
| 697 // - Passed() can be constructed from a scoper rvalue. |
| 698 // - Using Passed() gives Callback Ownership. |
| 699 // - Ownership is transferred from Callback to callee on the first Run(). |
| 700 // - Callback supports unbound arguments. |
| 701 TEST_F(BindTest, ScopedPtr) { |
| 702 int deletes = 0; |
| 703 |
| 704 // Tests the Passed() function's support for pointers. |
| 705 scoped_ptr<DeleteCounter> ptr(new DeleteCounter(&deletes)); |
| 706 Callback<scoped_ptr<DeleteCounter>(void)> unused_callback = |
| 707 Bind(&PassThru<scoped_ptr<DeleteCounter> >, Passed(&ptr)); |
| 708 EXPECT_FALSE(ptr.get()); |
| 709 EXPECT_EQ(0, deletes); |
| 710 |
| 711 // If we never invoke the Callback, it retains ownership and deletes. |
| 712 unused_callback.Reset(); |
| 713 EXPECT_EQ(1, deletes); |
| 714 |
| 715 // Tests the Passed() function's support for rvalues. |
| 716 deletes = 0; |
| 717 DeleteCounter* counter = new DeleteCounter(&deletes); |
| 718 Callback<scoped_ptr<DeleteCounter>(void)> callback = |
| 719 Bind(&PassThru<scoped_ptr<DeleteCounter> >, |
| 720 Passed(scoped_ptr<DeleteCounter>(counter))); |
| 721 EXPECT_FALSE(ptr.get()); |
| 722 EXPECT_EQ(0, deletes); |
| 723 |
| 724 // Check that ownership can be transferred back out. |
| 725 scoped_ptr<DeleteCounter> result = callback.Run(); |
| 726 ASSERT_EQ(counter, result.get()); |
| 727 EXPECT_EQ(0, deletes); |
| 728 |
| 729 // Resetting does not delete since ownership was transferred. |
| 730 callback.Reset(); |
| 731 EXPECT_EQ(0, deletes); |
| 732 |
| 733 // Ensure that we actually did get ownership. |
| 734 result.reset(); |
| 735 EXPECT_EQ(1, deletes); |
| 736 |
| 737 // Test unbound argument forwarding. |
| 738 Callback<scoped_ptr<DeleteCounter>(scoped_ptr<DeleteCounter>)> cb_unbound = |
| 739 Bind(&PassThru<scoped_ptr<DeleteCounter> >); |
| 740 ptr.reset(new DeleteCounter(&deletes)); |
| 741 cb_unbound.Run(ptr.Pass()); |
| 742 } |
| 743 |
687 // Argument Copy-constructor usage for non-reference parameters. | 744 // Argument Copy-constructor usage for non-reference parameters. |
688 // - Bound arguments are only copied once. | 745 // - Bound arguments are only copied once. |
689 // - Forwarded arguments are only copied once. | 746 // - Forwarded arguments are only copied once. |
690 // - Forwarded arguments with coerscions are only copied twice (once for the | 747 // - Forwarded arguments with coercions are only copied twice (once for the |
691 // coerscion, and one for the final dispatch). | 748 // coercion, and one for the final dispatch). |
692 TEST_F(BindTest, ArgumentCopies) { | 749 TEST_F(BindTest, ArgumentCopies) { |
693 int copies = 0; | 750 int copies = 0; |
694 int assigns = 0; | 751 int assigns = 0; |
695 | 752 |
696 CopyCounter counter(&copies, &assigns); | 753 CopyCounter counter(&copies, &assigns); |
697 | 754 |
698 Callback<void(void)> copy_cb = | 755 Callback<void(void)> copy_cb = |
699 Bind(&VoidPolymorphic1<CopyCounter>, counter); | 756 Bind(&VoidPolymorphic1<CopyCounter>, counter); |
700 EXPECT_GE(1, copies); | 757 EXPECT_GE(1, copies); |
701 EXPECT_EQ(0, assigns); | 758 EXPECT_EQ(0, assigns); |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
740 Callback<int(void)> fastcall_cb = Bind(&FastCallFunc, 1); | 797 Callback<int(void)> fastcall_cb = Bind(&FastCallFunc, 1); |
741 EXPECT_EQ(1, fastcall_cb.Run()); | 798 EXPECT_EQ(1, fastcall_cb.Run()); |
742 | 799 |
743 Callback<int(void)> stdcall_cb = Bind(&StdCallFunc, 2); | 800 Callback<int(void)> stdcall_cb = Bind(&StdCallFunc, 2); |
744 EXPECT_EQ(2, stdcall_cb.Run()); | 801 EXPECT_EQ(2, stdcall_cb.Run()); |
745 } | 802 } |
746 #endif | 803 #endif |
747 | 804 |
748 } // namespace | 805 } // namespace |
749 } // namespace base | 806 } // namespace base |
OLD | NEW |