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. 4 5 #include "base/bind.h" 6 7 #include <memory> 8 #include <utility> 9 #include <vector> 10 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/gtest_util.h" 17 #include "build/build_config.h" 18 #include "testing/gmock/include/gmock/gmock.h" 19 #include "testing/gtest/include/gtest/gtest.h" 20 21 using ::testing::_; 22 using ::testing::Mock; 23 using ::testing::ByMove; 24 using ::testing::Return; 25 using ::testing::StrictMock; 26 27 namespace base { 28 namespace { 29 30 class IncompleteType; 31 32 class NoRef { 33 public: 34 NoRef() {} 35 36 MOCK_METHOD0(VoidMethod0, void()); 37 MOCK_CONST_METHOD0(VoidConstMethod0, void()); 38 39 MOCK_METHOD0(IntMethod0, int()); 40 MOCK_CONST_METHOD0(IntConstMethod0, int()); 41 42 MOCK_METHOD1(VoidMethodWithIntArg, void(int)); 43 MOCK_METHOD0(UniquePtrMethod0, std::unique_ptr<int>()); 44 45 private: 46 // Particularly important in this test to ensure no copies are made. 47 DISALLOW_COPY_AND_ASSIGN(NoRef); 48 }; 49 50 class HasRef : public NoRef { 51 public: 52 HasRef() {} 53 54 MOCK_CONST_METHOD0(AddRef, void()); 55 MOCK_CONST_METHOD0(Release, bool()); 56 57 private: 58 // Particularly important in this test to ensure no copies are made. 59 DISALLOW_COPY_AND_ASSIGN(HasRef); 60 }; 61 62 class HasRefPrivateDtor : public HasRef { 63 private: 64 ~HasRefPrivateDtor() {} 65 }; 66 67 static const int kParentValue = 1; 68 static const int kChildValue = 2; 69 70 class Parent { 71 public: 72 virtual ~Parent() {} 73 void AddRef() const {} 74 void Release() const {} 75 virtual void VirtualSet() { value = kParentValue; } 76 void NonVirtualSet() { value = kParentValue; } 77 int value; 78 }; 79 80 class Child : public Parent { 81 public: 82 ~Child() override {} 83 void VirtualSet() override { value = kChildValue; } 84 void NonVirtualSet() { value = kChildValue; } 85 }; 86 87 class NoRefParent { 88 public: 89 virtual ~NoRefParent() {} 90 virtual void VirtualSet() { value = kParentValue; } 91 void NonVirtualSet() { value = kParentValue; } 92 int value; 93 }; 94 95 class NoRefChild : public NoRefParent { 96 public: 97 ~NoRefChild() override {} 98 private: 99 void VirtualSet() override { value = kChildValue; } 100 void NonVirtualSet() { value = kChildValue; } 101 }; 102 103 // Used for probing the number of copies and moves that occur if a type must be 104 // coerced during argument forwarding in the Run() methods. 105 struct DerivedCopyMoveCounter { 106 DerivedCopyMoveCounter(int* copies, 107 int* assigns, 108 int* move_constructs, 109 int* move_assigns) 110 : copies_(copies), 111 assigns_(assigns), 112 move_constructs_(move_constructs), 113 move_assigns_(move_assigns) {} 114 int* copies_; 115 int* assigns_; 116 int* move_constructs_; 117 int* move_assigns_; 118 }; 119 120 // Used for probing the number of copies and moves in an argument. 121 class CopyMoveCounter { 122 public: 123 CopyMoveCounter(int* copies, 124 int* assigns, 125 int* move_constructs, 126 int* move_assigns) 127 : copies_(copies), 128 assigns_(assigns), 129 move_constructs_(move_constructs), 130 move_assigns_(move_assigns) {} 131 132 CopyMoveCounter(const CopyMoveCounter& other) 133 : copies_(other.copies_), 134 assigns_(other.assigns_), 135 move_constructs_(other.move_constructs_), 136 move_assigns_(other.move_assigns_) { 137 (*copies_)++; 138 } 139 140 CopyMoveCounter(CopyMoveCounter&& other) 141 : copies_(other.copies_), 142 assigns_(other.assigns_), 143 move_constructs_(other.move_constructs_), 144 move_assigns_(other.move_assigns_) { 145 (*move_constructs_)++; 146 } 147 148 // Probing for copies from coercion. 149 explicit CopyMoveCounter(const DerivedCopyMoveCounter& other) 150 : copies_(other.copies_), 151 assigns_(other.assigns_), 152 move_constructs_(other.move_constructs_), 153 move_assigns_(other.move_assigns_) { 154 (*copies_)++; 155 } 156 157 // Probing for moves from coercion. 158 explicit CopyMoveCounter(DerivedCopyMoveCounter&& other) 159 : copies_(other.copies_), 160 assigns_(other.assigns_), 161 move_constructs_(other.move_constructs_), 162 move_assigns_(other.move_assigns_) { 163 (*move_constructs_)++; 164 } 165 166 const CopyMoveCounter& operator=(const CopyMoveCounter& rhs) { 167 copies_ = rhs.copies_; 168 assigns_ = rhs.assigns_; 169 move_constructs_ = rhs.move_constructs_; 170 move_assigns_ = rhs.move_assigns_; 171 172 (*assigns_)++; 173 174 return *this; 175 } 176 177 const CopyMoveCounter& operator=(CopyMoveCounter&& rhs) { 178 copies_ = rhs.copies_; 179 assigns_ = rhs.assigns_; 180 move_constructs_ = rhs.move_constructs_; 181 move_assigns_ = rhs.move_assigns_; 182 183 (*move_assigns_)++; 184 185 return *this; 186 } 187 188 int copies() const { 189 return *copies_; 190 } 191 192 private: 193 int* copies_; 194 int* assigns_; 195 int* move_constructs_; 196 int* move_assigns_; 197 }; 198 199 // Used for probing the number of copies in an argument. The instance is a 200 // copyable and non-movable type. 201 class CopyCounter { 202 public: 203 CopyCounter(int* copies, int* assigns) 204 : counter_(copies, assigns, nullptr, nullptr) {} 205 CopyCounter(const CopyCounter& other) : counter_(other.counter_) {} 206 CopyCounter& operator=(const CopyCounter& other) { 207 counter_ = other.counter_; 208 return *this; 209 } 210 211 explicit CopyCounter(const DerivedCopyMoveCounter& other) : counter_(other) {} 212 213 int copies() const { return counter_.copies(); } 214 215 private: 216 CopyMoveCounter counter_; 217 }; 218 219 // Used for probing the number of moves in an argument. The instance is a 220 // non-copyable and movable type. 221 class MoveCounter { 222 public: 223 MoveCounter(int* move_constructs, int* move_assigns) 224 : counter_(nullptr, nullptr, move_constructs, move_assigns) {} 225 MoveCounter(MoveCounter&& other) : counter_(std::move(other.counter_)) {} 226 MoveCounter& operator=(MoveCounter&& other) { 227 counter_ = std::move(other.counter_); 228 return *this; 229 } 230 231 explicit MoveCounter(DerivedCopyMoveCounter&& other) 232 : counter_(std::move(other)) {} 233 234 private: 235 CopyMoveCounter counter_; 236 }; 237 238 class DeleteCounter { 239 public: 240 explicit DeleteCounter(int* deletes) 241 : deletes_(deletes) { 242 } 243 244 ~DeleteCounter() { 245 (*deletes_)++; 246 } 247 248 void VoidMethod0() {} 249 250 private: 251 int* deletes_; 252 }; 253 254 template <typename T> 255 T PassThru(T scoper) { 256 return scoper; 257 } 258 259 // Some test functions that we can Bind to. 260 template <typename T> 261 T PolymorphicIdentity(T t) { 262 return t; 263 } 264 265 template <typename... Ts> 266 struct VoidPolymorphic { 267 static void Run(Ts... t) {} 268 }; 269 270 int Identity(int n) { 271 return n; 272 } 273 274 int ArrayGet(const int array[], int n) { 275 return array[n]; 276 } 277 278 int Sum(int a, int b, int c, int d, int e, int f) { 279 return a + b + c + d + e + f; 280 } 281 282 const char* CStringIdentity(const char* s) { 283 return s; 284 } 285 286 int GetCopies(const CopyMoveCounter& counter) { 287 return counter.copies(); 288 } 289 290 int UnwrapNoRefParent(NoRefParent p) { 291 return p.value; 292 } 293 294 int UnwrapNoRefParentPtr(NoRefParent* p) { 295 return p->value; 296 } 297 298 int UnwrapNoRefParentConstRef(const NoRefParent& p) { 299 return p.value; 300 } 301 302 void RefArgSet(int &n) { 303 n = 2; 304 } 305 306 void PtrArgSet(int *n) { 307 *n = 2; 308 } 309 310 int FunctionWithWeakFirstParam(WeakPtr<NoRef> o, int n) { 311 return n; 312 } 313 314 int FunctionWithScopedRefptrFirstParam(const scoped_refptr<HasRef>& o, int n) { 315 return n; 316 } 317 318 void TakesACallback(const Closure& callback) { 319 callback.Run(); 320 } 321 322 class BindTest : public ::testing::Test { 323 public: 324 BindTest() { 325 const_has_ref_ptr_ = &has_ref_; 326 const_no_ref_ptr_ = &no_ref_; 327 static_func_mock_ptr = &static_func_mock_; 328 } 329 330 virtual ~BindTest() { 331 } 332 333 static void VoidFunc0() { 334 static_func_mock_ptr->VoidMethod0(); 335 } 336 337 static int IntFunc0() { return static_func_mock_ptr->IntMethod0(); } 338 339 protected: 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_; 345 346 // Used by the static functions to perform expectations. 347 static StrictMock<NoRef>* static_func_mock_ptr; 348 349 private: 350 DISALLOW_COPY_AND_ASSIGN(BindTest); 351 }; 352 353 StrictMock<NoRef>* BindTest::static_func_mock_ptr; 354 StrictMock<NoRef>* g_func_mock_ptr; 355 356 void VoidFunc0() { 357 g_func_mock_ptr->VoidMethod0(); 358 } 359 360 int IntFunc0() { 361 return g_func_mock_ptr->IntMethod0(); 362 } 363 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)); 367 368 Callback<int(int, int, int, int, int, int)> c1 = Bind(&Sum); 369 EXPECT_EQ(69, c1.Run(14, 13, 12, 11, 10, 9)); 370 371 Callback<int(int, int, int)> c2 = Bind(c1, 32, 16, 8); 372 EXPECT_EQ(86, c2.Run(11, 10, 9)); 373 374 Callback<int()> c3 = Bind(c2, 4, 2, 1); 375 EXPECT_EQ(63, c3.Run()); 376 } 377 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) { 382 int n = 0; 383 RepeatingClosure cb = BindRepeating(&TakesACallback, 384 BindRepeating(&PtrArgSet, &n)); 385 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. 390 cb.Run(); 391 EXPECT_EQ(2, n); 392 393 n = 0; 394 cb.Run(); 395 EXPECT_EQ(2, n); 396 } 397 398 TEST_F(BindTest, RepeatingCallbackBasicTest) { 399 RepeatingCallback<int(int)> c0 = BindRepeating(&Sum, 1, 2, 4, 8, 16); 400 401 // RepeatingCallback can run via a lvalue-reference. 402 EXPECT_EQ(63, c0.Run(32)); 403 404 // It is valid to call a RepeatingCallback more than once. 405 EXPECT_EQ(54, c0.Run(23)); 406 407 // BindRepeating can handle a RepeatingCallback as the target functor. 408 RepeatingCallback<int()> c1 = BindRepeating(c0, 11); 409 410 // RepeatingCallback can run via a rvalue-reference. 411 EXPECT_EQ(42, std::move(c1).Run()); 412 413 // BindRepeating can handle a rvalue-reference of RepeatingCallback. 414 EXPECT_EQ(32, BindRepeating(std::move(c0), 1).Run()); 415 } 416 417 TEST_F(BindTest, OnceCallbackBasicTest) { 418 OnceCallback<int(int)> c0 = BindOnce(&Sum, 1, 2, 4, 8, 16); 419 420 // OnceCallback can run via a rvalue-reference. 421 EXPECT_EQ(63, std::move(c0).Run(32)); 422 423 // After running via the rvalue-reference, the value of the OnceCallback 424 // is undefined. The implementation simply clears the instance after the 425 // invocation. 426 EXPECT_TRUE(c0.is_null()); 427 428 c0 = BindOnce(&Sum, 2, 3, 5, 7, 11); 429 430 // BindOnce can handle a rvalue-reference of OnceCallback as the target 431 // functor. 432 OnceCallback<int()> c1 = BindOnce(std::move(c0), 13); 433 EXPECT_EQ(41, std::move(c1).Run()); 434 435 RepeatingCallback<int(int)> c2 = BindRepeating(&Sum, 2, 3, 5, 7, 11); 436 EXPECT_EQ(41, BindOnce(c2, 13).Run()); 437 } 438 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_, IntMethod0()).WillOnce(Return(10)); 450 EXPECT_CALL(has_ref_, IntConstMethod0()).WillOnce(Return(11)); 451 EXPECT_CALL(no_ref_, IntMethod0()).WillOnce(Return(12)); 452 EXPECT_CALL(no_ref_, IntConstMethod0()).WillOnce(Return(13)); 453 454 RepeatingClosure normal_func_cb = BindRepeating(IgnoreResult(&IntFunc0)); 455 normal_func_cb.Run(); 456 457 RepeatingClosure non_void_method_cb = 458 BindRepeating(IgnoreResult(&HasRef::IntMethod0), &has_ref_); 459 non_void_method_cb.Run(); 460 461 RepeatingClosure non_void_const_method_cb = 462 BindRepeating(IgnoreResult(&HasRef::IntConstMethod0), &has_ref_); 463 non_void_const_method_cb.Run(); 464 465 WeakPtrFactory<NoRef> weak_factory(&no_ref_); 466 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_); 467 468 RepeatingClosure non_void_weak_method_cb = 469 BindRepeating(IgnoreResult(&NoRef::IntMethod0), 470 weak_factory.GetWeakPtr()); 471 non_void_weak_method_cb.Run(); 472 473 RepeatingClosure non_void_weak_const_method_cb = 474 BindRepeating(IgnoreResult(&NoRef::IntConstMethod0), 475 weak_factory.GetWeakPtr()); 476 non_void_weak_const_method_cb.Run(); 477 478 weak_factory.InvalidateWeakPtrs(); 479 non_void_weak_const_method_cb.Run(); 480 non_void_weak_method_cb.Run(); 481 } 482 483 TEST_F(BindTest, IgnoreResultForOnce) { 484 EXPECT_CALL(static_func_mock_, IntMethod0()).WillOnce(Return(1337)); 485 EXPECT_CALL(has_ref_, AddRef()).Times(2); 486 EXPECT_CALL(has_ref_, Release()).Times(2); 487 EXPECT_CALL(has_ref_, IntMethod0()).WillOnce(Return(10)); 488 EXPECT_CALL(has_ref_, IntConstMethod0()).WillOnce(Return(11)); 489 490 OnceClosure normal_func_cb = BindOnce(IgnoreResult(&IntFunc0)); 491 std::move(normal_func_cb).Run(); 492 493 OnceClosure non_void_method_cb = 494 BindOnce(IgnoreResult(&HasRef::IntMethod0), &has_ref_); 495 std::move(non_void_method_cb).Run(); 496 497 OnceClosure non_void_const_method_cb = 498 BindOnce(IgnoreResult(&HasRef::IntConstMethod0), &has_ref_); 499 std::move(non_void_const_method_cb).Run(); 500 501 WeakPtrFactory<NoRef> weak_factory(&no_ref_); 502 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_); 503 504 OnceClosure non_void_weak_method_cb = 505 BindOnce(IgnoreResult(&NoRef::IntMethod0), 506 weak_factory.GetWeakPtr()); 507 OnceClosure non_void_weak_const_method_cb = 508 BindOnce(IgnoreResult(&NoRef::IntConstMethod0), 509 weak_factory.GetWeakPtr()); 510 511 weak_factory.InvalidateWeakPtrs(); 512 std::move(non_void_weak_const_method_cb).Run(); 513 std::move(non_void_weak_method_cb).Run(); 514 } 515 516 // Functions that take reference parameters. 517 // - Forced reference parameter type still stores a copy. 518 // - Forced const reference parameter type still stores a copy. 519 TEST_F(BindTest, ReferenceArgumentBindingForRepeating) { 520 int n = 1; 521 int& ref_n = n; 522 const int& const_ref_n = n; 523 524 RepeatingCallback<int()> ref_copies_cb = BindRepeating(&Identity, ref_n); 525 EXPECT_EQ(n, ref_copies_cb.Run()); 526 n++; 527 EXPECT_EQ(n - 1, ref_copies_cb.Run()); 528 529 RepeatingCallback<int()> const_ref_copies_cb = 530 BindRepeating(&Identity, const_ref_n); 531 EXPECT_EQ(n, const_ref_copies_cb.Run()); 532 n++; 533 EXPECT_EQ(n - 1, const_ref_copies_cb.Run()); 534 } 535 536 TEST_F(BindTest, ReferenceArgumentBindingForOnce) { 537 int n = 1; 538 int& ref_n = n; 539 const int& const_ref_n = n; 540 541 OnceCallback<int()> ref_copies_cb = BindOnce(&Identity, ref_n); 542 n++; 543 EXPECT_EQ(n - 1, std::move(ref_copies_cb).Run()); 544 545 OnceCallback<int()> const_ref_copies_cb = 546 BindOnce(&Identity, const_ref_n); 547 n++; 548 EXPECT_EQ(n - 1, std::move(const_ref_copies_cb).Run()); 549 } 550 551 // Check that we can pass in arrays and have them be stored as a pointer. 552 // - Array of values stores a pointer. 553 // - Array of const values stores a pointer. 554 TEST_F(BindTest, ArrayArgumentBindingForRepeating) { 555 int array[4] = {1, 1, 1, 1}; 556 const int (*const_array_ptr)[4] = &array; 557 558 RepeatingCallback<int()> array_cb = BindRepeating(&ArrayGet, array, 1); 559 EXPECT_EQ(1, array_cb.Run()); 560 561 RepeatingCallback<int()> const_array_cb = 562 BindRepeating(&ArrayGet, *const_array_ptr, 1); 563 EXPECT_EQ(1, const_array_cb.Run()); 564 565 array[1] = 3; 566 EXPECT_EQ(3, array_cb.Run()); 567 EXPECT_EQ(3, const_array_cb.Run()); 568 } 569 570 TEST_F(BindTest, ArrayArgumentBindingForOnce) { 571 int array[4] = {1, 1, 1, 1}; 572 const int (*const_array_ptr)[4] = &array; 573 574 OnceCallback<int()> array_cb = BindOnce(&ArrayGet, array, 1); 575 OnceCallback<int()> const_array_cb = 576 BindOnce(&ArrayGet, *const_array_ptr, 1); 577 578 array[1] = 3; 579 EXPECT_EQ(3, std::move(array_cb).Run()); 580 EXPECT_EQ(3, std::move(const_array_cb).Run()); 581 } 582 583 // WeakPtr() support. 584 // - Method bound to WeakPtr<> to non-const object. 585 // - Const method bound to WeakPtr<> to non-const object. 586 // - Const method bound to WeakPtr<> to const object. 587 // - Normal Function with WeakPtr<> as P1 can have return type and is 588 // not canceled. 589 TEST_F(BindTest, WeakPtrForRepeating) { 590 EXPECT_CALL(no_ref_, VoidMethod0()); 591 EXPECT_CALL(no_ref_, VoidConstMethod0()).Times(2); 592 593 WeakPtrFactory<NoRef> weak_factory(&no_ref_); 594 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_); 595 596 RepeatingClosure method_cb = 597 BindRepeating(&NoRef::VoidMethod0, weak_factory.GetWeakPtr()); 598 method_cb.Run(); 599 600 RepeatingClosure const_method_cb = 601 BindRepeating(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr()); 602 const_method_cb.Run(); 603 604 RepeatingClosure const_method_const_ptr_cb = 605 BindRepeating(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr()); 606 const_method_const_ptr_cb.Run(); 607 608 RepeatingCallback<int(int)> normal_func_cb = 609 BindRepeating(&FunctionWithWeakFirstParam, weak_factory.GetWeakPtr()); 610 EXPECT_EQ(1, normal_func_cb.Run(1)); 611 612 weak_factory.InvalidateWeakPtrs(); 613 const_weak_factory.InvalidateWeakPtrs(); 614 615 method_cb.Run(); 616 const_method_cb.Run(); 617 const_method_const_ptr_cb.Run(); 618 619 // Still runs even after the pointers are invalidated. 620 EXPECT_EQ(2, normal_func_cb.Run(2)); 621 } 622 623 TEST_F(BindTest, WeakPtrForOnce) { 624 WeakPtrFactory<NoRef> weak_factory(&no_ref_); 625 WeakPtrFactory<const NoRef> const_weak_factory(const_no_ref_ptr_); 626 627 OnceClosure method_cb = 628 BindOnce(&NoRef::VoidMethod0, weak_factory.GetWeakPtr()); 629 OnceClosure const_method_cb = 630 BindOnce(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr()); 631 OnceClosure const_method_const_ptr_cb = 632 BindOnce(&NoRef::VoidConstMethod0, const_weak_factory.GetWeakPtr()); 633 Callback<int(int)> normal_func_cb = 634 Bind(&FunctionWithWeakFirstParam, weak_factory.GetWeakPtr()); 635 636 weak_factory.InvalidateWeakPtrs(); 637 const_weak_factory.InvalidateWeakPtrs(); 638 639 std::move(method_cb).Run(); 640 std::move(const_method_cb).Run(); 641 std::move(const_method_const_ptr_cb).Run(); 642 643 // Still runs even after the pointers are invalidated. 644 EXPECT_EQ(2, std::move(normal_func_cb).Run(2)); 645 } 646 647 // ConstRef() wrapper support. 648 // - Binding w/o ConstRef takes a copy. 649 // - Binding a ConstRef takes a reference. 650 // - Binding ConstRef to a function ConstRef does not copy on invoke. 651 TEST_F(BindTest, ConstRefForRepeating) { 652 int n = 1; 653 654 RepeatingCallback<int()> copy_cb = BindRepeating(&Identity, n); 655 RepeatingCallback<int()> const_ref_cb = BindRepeating(&Identity, ConstRef(n)); 656 EXPECT_EQ(n, copy_cb.Run()); 657 EXPECT_EQ(n, const_ref_cb.Run()); 658 n++; 659 EXPECT_EQ(n - 1, copy_cb.Run()); 660 EXPECT_EQ(n, const_ref_cb.Run()); 661 662 int copies = 0; 663 int assigns = 0; 664 int move_constructs = 0; 665 int move_assigns = 0; 666 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns); 667 RepeatingCallback<int()> all_const_ref_cb = 668 BindRepeating(&GetCopies, ConstRef(counter)); 669 EXPECT_EQ(0, all_const_ref_cb.Run()); 670 EXPECT_EQ(0, copies); 671 EXPECT_EQ(0, assigns); 672 EXPECT_EQ(0, move_constructs); 673 EXPECT_EQ(0, move_assigns); 674 } 675 676 TEST_F(BindTest, ConstRefForOnce) { 677 int n = 1; 678 679 OnceCallback<int()> copy_cb = BindOnce(&Identity, n); 680 OnceCallback<int()> const_ref_cb = BindOnce(&Identity, ConstRef(n)); 681 n++; 682 EXPECT_EQ(n - 1, std::move(copy_cb).Run()); 683 EXPECT_EQ(n, std::move(const_ref_cb).Run()); 684 685 int copies = 0; 686 int assigns = 0; 687 int move_constructs = 0; 688 int move_assigns = 0; 689 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns); 690 OnceCallback<int()> all_const_ref_cb = 691 BindOnce(&GetCopies, ConstRef(counter)); 692 EXPECT_EQ(0, std::move(all_const_ref_cb).Run()); 693 EXPECT_EQ(0, copies); 694 EXPECT_EQ(0, assigns); 695 EXPECT_EQ(0, move_constructs); 696 EXPECT_EQ(0, move_assigns); 697 } 698 699 // Test Owned() support. 700 TEST_F(BindTest, OwnedForRepeating) { 701 int deletes = 0; 702 DeleteCounter* counter = new DeleteCounter(&deletes); 703 704 // If we don't capture, delete happens on Callback destruction/reset. 705 // return the same value. 706 RepeatingCallback<DeleteCounter*()> no_capture_cb = 707 BindRepeating(&PolymorphicIdentity<DeleteCounter*>, Owned(counter)); 708 ASSERT_EQ(counter, no_capture_cb.Run()); 709 ASSERT_EQ(counter, no_capture_cb.Run()); 710 EXPECT_EQ(0, deletes); 711 no_capture_cb.Reset(); // This should trigger a delete. 712 EXPECT_EQ(1, deletes); 713 714 deletes = 0; 715 counter = new DeleteCounter(&deletes); 716 RepeatingClosure own_object_cb = 717 BindRepeating(&DeleteCounter::VoidMethod0, Owned(counter)); 718 own_object_cb.Run(); 719 EXPECT_EQ(0, deletes); 720 own_object_cb.Reset(); 721 EXPECT_EQ(1, deletes); 722 } 723 724 TEST_F(BindTest, OwnedForOnce) { 725 int deletes = 0; 726 DeleteCounter* counter = new DeleteCounter(&deletes); 727 728 // If we don't capture, delete happens on Callback destruction/reset. 729 // return the same value. 730 OnceCallback<DeleteCounter*()> no_capture_cb = 731 BindOnce(&PolymorphicIdentity<DeleteCounter*>, Owned(counter)); 732 EXPECT_EQ(0, deletes); 733 no_capture_cb.Reset(); // This should trigger a delete. 734 EXPECT_EQ(1, deletes); 735 736 deletes = 0; 737 counter = new DeleteCounter(&deletes); 738 OnceClosure own_object_cb = 739 BindOnce(&DeleteCounter::VoidMethod0, Owned(counter)); 740 EXPECT_EQ(0, deletes); 741 own_object_cb.Reset(); 742 EXPECT_EQ(1, deletes); 743 } 744 745 template <typename T> 746 class BindVariantsTest : public ::testing::Test { 747 }; 748 749 struct RepeatingTestConfig { 750 template <typename Signature> 751 using CallbackType = RepeatingCallback<Signature>; 752 using ClosureType = RepeatingClosure; 753 754 template <typename F, typename... Args> 755 static CallbackType<MakeUnboundRunType<F, Args...>> 756 Bind(F&& f, Args&&... args) { 757 return BindRepeating(std::forward<F>(f), std::forward<Args>(args)...); 758 } 759 }; 760 761 struct OnceTestConfig { 762 template <typename Signature> 763 using CallbackType = OnceCallback<Signature>; 764 using ClosureType = OnceClosure; 765 766 template <typename F, typename... Args> 767 static CallbackType<MakeUnboundRunType<F, Args...>> 768 Bind(F&& f, Args&&... args) { 769 return BindOnce(std::forward<F>(f), std::forward<Args>(args)...); 770 } 771 }; 772 773 using BindVariantsTestConfig = ::testing::Types< 774 RepeatingTestConfig, OnceTestConfig>; 775 TYPED_TEST_CASE(BindVariantsTest, BindVariantsTestConfig); 776 777 template <typename TypeParam, typename Signature> 778 using CallbackType = typename TypeParam::template CallbackType<Signature>; 779 780 // Function type support. 781 // - Normal function. 782 // - Normal function bound with non-refcounted first argument. 783 // - Method bound to non-const object. 784 // - Method bound to scoped_refptr. 785 // - Const method bound to non-const object. 786 // - Const method bound to const object. 787 // - Derived classes can be used with pointers to non-virtual base functions. 788 // - Derived classes can be used with pointers to virtual base functions (and 789 // preserve virtual dispatch). 790 TYPED_TEST(BindVariantsTest, FunctionTypeSupport) { 791 using ClosureType = typename TypeParam::ClosureType; 792 793 StrictMock<HasRef> has_ref; 794 StrictMock<NoRef> no_ref; 795 StrictMock<NoRef> static_func_mock; 796 const HasRef* const_has_ref_ptr = &has_ref; 797 g_func_mock_ptr = &static_func_mock; 798 799 EXPECT_CALL(static_func_mock, VoidMethod0()); 800 EXPECT_CALL(has_ref, AddRef()).Times(4); 801 EXPECT_CALL(has_ref, Release()).Times(4); 802 EXPECT_CALL(has_ref, VoidMethod0()).Times(2); 803 EXPECT_CALL(has_ref, VoidConstMethod0()).Times(2); 804 805 ClosureType normal_cb = TypeParam::Bind(&VoidFunc0); 806 CallbackType<TypeParam, NoRef*()> normal_non_refcounted_cb = 807 TypeParam::Bind(&PolymorphicIdentity<NoRef*>, &no_ref); 808 std::move(normal_cb).Run(); 809 EXPECT_EQ(&no_ref, std::move(normal_non_refcounted_cb).Run()); 810 811 ClosureType method_cb = TypeParam::Bind(&HasRef::VoidMethod0, &has_ref); 812 ClosureType method_refptr_cb = TypeParam::Bind(&HasRef::VoidMethod0, 813 make_scoped_refptr(&has_ref)); 814 ClosureType const_method_nonconst_obj_cb = 815 TypeParam::Bind(&HasRef::VoidConstMethod0, &has_ref); 816 ClosureType const_method_const_obj_cb = 817 TypeParam::Bind(&HasRef::VoidConstMethod0, const_has_ref_ptr); 818 std::move(method_cb).Run(); 819 std::move(method_refptr_cb).Run(); 820 std::move(const_method_nonconst_obj_cb).Run(); 821 std::move(const_method_const_obj_cb).Run(); 822 823 Child child; 824 child.value = 0; 825 ClosureType virtual_set_cb = TypeParam::Bind(&Parent::VirtualSet, &child); 826 std::move(virtual_set_cb).Run(); 827 EXPECT_EQ(kChildValue, child.value); 828 829 child.value = 0; 830 ClosureType non_virtual_set_cb = 831 TypeParam::Bind(&Parent::NonVirtualSet, &child); 832 std::move(non_virtual_set_cb).Run(); 833 EXPECT_EQ(kParentValue, child.value); 834 } 835 836 // Return value support. 837 // - Function with return value. 838 // - Method with return value. 839 // - Const method with return value. 840 // - Move-only return value. 841 TYPED_TEST(BindVariantsTest, ReturnValues) { 842 StrictMock<NoRef> static_func_mock; 843 StrictMock<HasRef> has_ref; 844 g_func_mock_ptr = &static_func_mock; 845 const HasRef* const_has_ref_ptr = &has_ref; 846 847 EXPECT_CALL(static_func_mock, IntMethod0()).WillOnce(Return(1337)); 848 EXPECT_CALL(has_ref, AddRef()).Times(4); 849 EXPECT_CALL(has_ref, Release()).Times(4); 850 EXPECT_CALL(has_ref, IntMethod0()).WillOnce(Return(31337)); 851 EXPECT_CALL(has_ref, IntConstMethod0()) 852 .WillOnce(Return(41337)) 853 .WillOnce(Return(51337)); 854 EXPECT_CALL(has_ref, UniquePtrMethod0()) 855 .WillOnce(Return(ByMove(MakeUnique<int>(42)))); 856 857 CallbackType<TypeParam, int()> normal_cb = TypeParam::Bind(&IntFunc0); 858 CallbackType<TypeParam, int()> method_cb = 859 TypeParam::Bind(&HasRef::IntMethod0, &has_ref); 860 CallbackType<TypeParam, int()> const_method_nonconst_obj_cb = 861 TypeParam::Bind(&HasRef::IntConstMethod0, &has_ref); 862 CallbackType<TypeParam, int()> const_method_const_obj_cb = 863 TypeParam::Bind(&HasRef::IntConstMethod0, const_has_ref_ptr); 864 CallbackType<TypeParam, std::unique_ptr<int>()> move_only_rv_cb = 865 TypeParam::Bind(&HasRef::UniquePtrMethod0, &has_ref); 866 EXPECT_EQ(1337, std::move(normal_cb).Run()); 867 EXPECT_EQ(31337, std::move(method_cb).Run()); 868 EXPECT_EQ(41337, std::move(const_method_nonconst_obj_cb).Run()); 869 EXPECT_EQ(51337, std::move(const_method_const_obj_cb).Run()); 870 EXPECT_EQ(42, *std::move(move_only_rv_cb).Run()); 871 } 872 873 // Argument binding tests. 874 // - Argument binding to primitive. 875 // - Argument binding to primitive pointer. 876 // - Argument binding to a literal integer. 877 // - Argument binding to a literal string. 878 // - Argument binding with template function. 879 // - Argument binding to an object. 880 // - Argument binding to pointer to incomplete type. 881 // - Argument gets type converted. 882 // - Pointer argument gets converted. 883 // - Const Reference forces conversion. 884 TYPED_TEST(BindVariantsTest, ArgumentBinding) { 885 int n = 2; 886 887 EXPECT_EQ(n, TypeParam::Bind(&Identity, n).Run()); 888 EXPECT_EQ(&n, TypeParam::Bind(&PolymorphicIdentity<int*>, &n).Run()); 889 EXPECT_EQ(3, TypeParam::Bind(&Identity, 3).Run()); 890 EXPECT_STREQ("hi", TypeParam::Bind(&CStringIdentity, "hi").Run()); 891 EXPECT_EQ(4, TypeParam::Bind(&PolymorphicIdentity<int>, 4).Run()); 892 893 NoRefParent p; 894 p.value = 5; 895 EXPECT_EQ(5, TypeParam::Bind(&UnwrapNoRefParent, p).Run()); 896 897 IncompleteType* incomplete_ptr = reinterpret_cast<IncompleteType*>(123); 898 EXPECT_EQ(incomplete_ptr, 899 TypeParam::Bind(&PolymorphicIdentity<IncompleteType*>, 900 incomplete_ptr).Run()); 901 902 NoRefChild c; 903 c.value = 6; 904 EXPECT_EQ(6, TypeParam::Bind(&UnwrapNoRefParent, c).Run()); 905 906 c.value = 7; 907 EXPECT_EQ(7, TypeParam::Bind(&UnwrapNoRefParentPtr, &c).Run()); 908 909 c.value = 8; 910 EXPECT_EQ(8, TypeParam::Bind(&UnwrapNoRefParentConstRef, c).Run()); 911 } 912 913 // Unbound argument type support tests. 914 // - Unbound value. 915 // - Unbound pointer. 916 // - Unbound reference. 917 // - Unbound const reference. 918 // - Unbound unsized array. 919 // - Unbound sized array. 920 // - Unbound array-of-arrays. 921 TYPED_TEST(BindVariantsTest, UnboundArgumentTypeSupport) { 922 CallbackType<TypeParam, void(int)> unbound_value_cb = 923 TypeParam::Bind(&VoidPolymorphic<int>::Run); 924 CallbackType<TypeParam, void(int*)> unbound_pointer_cb = 925 TypeParam::Bind(&VoidPolymorphic<int*>::Run); 926 CallbackType<TypeParam, void(int&)> unbound_ref_cb = 927 TypeParam::Bind(&VoidPolymorphic<int&>::Run); 928 CallbackType<TypeParam, void(const int&)> unbound_const_ref_cb = 929 TypeParam::Bind(&VoidPolymorphic<const int&>::Run); 930 CallbackType<TypeParam, void(int[])> unbound_unsized_array_cb = 931 TypeParam::Bind(&VoidPolymorphic<int[]>::Run); 932 CallbackType<TypeParam, void(int[2])> unbound_sized_array_cb = 933 TypeParam::Bind(&VoidPolymorphic<int[2]>::Run); 934 CallbackType<TypeParam, void(int[][2])> unbound_array_of_arrays_cb = 935 TypeParam::Bind(&VoidPolymorphic<int[][2]>::Run); 936 CallbackType<TypeParam, void(int&)> unbound_ref_with_bound_arg = 937 TypeParam::Bind(&VoidPolymorphic<int, int&>::Run, 1); 938 } 939 940 // Function with unbound reference parameter. 941 // - Original parameter is modified by callback. 942 TYPED_TEST(BindVariantsTest, UnboundReferenceSupport) { 943 int n = 0; 944 CallbackType<TypeParam, void(int&)> unbound_ref_cb = 945 TypeParam::Bind(&RefArgSet); 946 std::move(unbound_ref_cb).Run(n); 947 EXPECT_EQ(2, n); 948 } 949 950 // Unretained() wrapper support. 951 // - Method bound to Unretained() non-const object. 952 // - Const method bound to Unretained() non-const object. 953 // - Const method bound to Unretained() const object. 954 TYPED_TEST(BindVariantsTest, Unretained) { 955 StrictMock<NoRef> no_ref; 956 const NoRef* const_no_ref_ptr = &no_ref; 957 958 EXPECT_CALL(no_ref, VoidMethod0()); 959 EXPECT_CALL(no_ref, VoidConstMethod0()).Times(2); 960 961 TypeParam::Bind(&NoRef::VoidMethod0, Unretained(&no_ref)).Run(); 962 TypeParam::Bind(&NoRef::VoidConstMethod0, Unretained(&no_ref)).Run(); 963 TypeParam::Bind(&NoRef::VoidConstMethod0, Unretained(const_no_ref_ptr)).Run(); 964 } 965 966 TYPED_TEST(BindVariantsTest, ScopedRefptr) { 967 StrictMock<HasRef> has_ref; 968 EXPECT_CALL(has_ref, AddRef()).Times(1); 969 EXPECT_CALL(has_ref, Release()).Times(1); 970 971 const scoped_refptr<HasRef> refptr(&has_ref); 972 CallbackType<TypeParam, int()> scoped_refptr_const_ref_cb = 973 TypeParam::Bind(&FunctionWithScopedRefptrFirstParam, 974 base::ConstRef(refptr), 1); 975 EXPECT_EQ(1, std::move(scoped_refptr_const_ref_cb).Run()); 976 } 977 978 TYPED_TEST(BindVariantsTest, UniquePtrReceiver) { 979 std::unique_ptr<StrictMock<NoRef>> no_ref(new StrictMock<NoRef>); 980 EXPECT_CALL(*no_ref, VoidMethod0()).Times(1); 981 TypeParam::Bind(&NoRef::VoidMethod0, std::move(no_ref)).Run(); 982 } 983 984 // Tests for Passed() wrapper support: 985 // - Passed() can be constructed from a pointer to scoper. 986 // - Passed() can be constructed from a scoper rvalue. 987 // - Using Passed() gives Callback Ownership. 988 // - Ownership is transferred from Callback to callee on the first Run(). 989 // - Callback supports unbound arguments. 990 template <typename T> 991 class BindMoveOnlyTypeTest : public ::testing::Test { 992 }; 993 994 struct CustomDeleter { 995 void operator()(DeleteCounter* c) { delete c; } 996 }; 997 998 using MoveOnlyTypesToTest = 999 ::testing::Types<std::unique_ptr<DeleteCounter>, 1000 std::unique_ptr<DeleteCounter, CustomDeleter>>; 1001 TYPED_TEST_CASE(BindMoveOnlyTypeTest, MoveOnlyTypesToTest); 1002 1003 TYPED_TEST(BindMoveOnlyTypeTest, PassedToBoundCallback) { 1004 int deletes = 0; 1005 1006 TypeParam ptr(new DeleteCounter(&deletes)); 1007 Callback<TypeParam()> callback = Bind(&PassThru<TypeParam>, Passed(&ptr)); 1008 EXPECT_FALSE(ptr.get()); 1009 EXPECT_EQ(0, deletes); 1010 1011 // If we never invoke the Callback, it retains ownership and deletes. 1012 callback.Reset(); 1013 EXPECT_EQ(1, deletes); 1014 } 1015 1016 TYPED_TEST(BindMoveOnlyTypeTest, PassedWithRvalue) { 1017 int deletes = 0; 1018 Callback<TypeParam()> callback = Bind( 1019 &PassThru<TypeParam>, Passed(TypeParam(new DeleteCounter(&deletes)))); 1020 EXPECT_EQ(0, deletes); 1021 1022 // If we never invoke the Callback, it retains ownership and deletes. 1023 callback.Reset(); 1024 EXPECT_EQ(1, deletes); 1025 } 1026 1027 // Check that ownership can be transferred back out. 1028 TYPED_TEST(BindMoveOnlyTypeTest, ReturnMoveOnlyType) { 1029 int deletes = 0; 1030 DeleteCounter* counter = new DeleteCounter(&deletes); 1031 Callback<TypeParam()> callback = 1032 Bind(&PassThru<TypeParam>, Passed(TypeParam(counter))); 1033 TypeParam result = callback.Run(); 1034 ASSERT_EQ(counter, result.get()); 1035 EXPECT_EQ(0, deletes); 1036 1037 // Resetting does not delete since ownership was transferred. 1038 callback.Reset(); 1039 EXPECT_EQ(0, deletes); 1040 1041 // Ensure that we actually did get ownership. 1042 result.reset(); 1043 EXPECT_EQ(1, deletes); 1044 } 1045 1046 TYPED_TEST(BindMoveOnlyTypeTest, UnboundForwarding) { 1047 int deletes = 0; 1048 TypeParam ptr(new DeleteCounter(&deletes)); 1049 // Test unbound argument forwarding. 1050 Callback<TypeParam(TypeParam)> cb_unbound = Bind(&PassThru<TypeParam>); 1051 cb_unbound.Run(std::move(ptr)); 1052 EXPECT_EQ(1, deletes); 1053 } 1054 1055 void VerifyVector(const std::vector<std::unique_ptr<int>>& v) { 1056 ASSERT_EQ(1u, v.size()); 1057 EXPECT_EQ(12345, *v[0]); 1058 } 1059 1060 std::vector<std::unique_ptr<int>> AcceptAndReturnMoveOnlyVector( 1061 std::vector<std::unique_ptr<int>> v) { 1062 VerifyVector(v); 1063 return v; 1064 } 1065 1066 // Test that a vector containing move-only types can be used with Callback. 1067 TEST_F(BindTest, BindMoveOnlyVector) { 1068 using MoveOnlyVector = std::vector<std::unique_ptr<int>>; 1069 1070 MoveOnlyVector v; 1071 v.push_back(WrapUnique(new int(12345))); 1072 1073 // Early binding should work: 1074 base::Callback<MoveOnlyVector()> bound_cb = 1075 base::Bind(&AcceptAndReturnMoveOnlyVector, Passed(&v)); 1076 MoveOnlyVector intermediate_result = bound_cb.Run(); 1077 VerifyVector(intermediate_result); 1078 1079 // As should passing it as an argument to Run(): 1080 base::Callback<MoveOnlyVector(MoveOnlyVector)> unbound_cb = 1081 base::Bind(&AcceptAndReturnMoveOnlyVector); 1082 MoveOnlyVector final_result = unbound_cb.Run(std::move(intermediate_result)); 1083 VerifyVector(final_result); 1084 } 1085 1086 // Argument copy-constructor usage for non-reference copy-only parameters. 1087 // - Bound arguments are only copied once. 1088 // - Forwarded arguments are only copied once. 1089 // - Forwarded arguments with coercions are only copied twice (once for the 1090 // coercion, and one for the final dispatch). 1091 TEST_F(BindTest, ArgumentCopies) { 1092 int copies = 0; 1093 int assigns = 0; 1094 1095 CopyCounter counter(&copies, &assigns); 1096 Bind(&VoidPolymorphic<CopyCounter>::Run, counter); 1097 EXPECT_EQ(1, copies); 1098 EXPECT_EQ(0, assigns); 1099 1100 copies = 0; 1101 assigns = 0; 1102 Bind(&VoidPolymorphic<CopyCounter>::Run, CopyCounter(&copies, &assigns)); 1103 EXPECT_EQ(1, copies); 1104 EXPECT_EQ(0, assigns); 1105 1106 copies = 0; 1107 assigns = 0; 1108 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(counter); 1109 EXPECT_EQ(2, copies); 1110 EXPECT_EQ(0, assigns); 1111 1112 copies = 0; 1113 assigns = 0; 1114 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(CopyCounter(&copies, &assigns)); 1115 EXPECT_EQ(1, copies); 1116 EXPECT_EQ(0, assigns); 1117 1118 copies = 0; 1119 assigns = 0; 1120 DerivedCopyMoveCounter derived(&copies, &assigns, nullptr, nullptr); 1121 Bind(&VoidPolymorphic<CopyCounter>::Run).Run(CopyCounter(derived)); 1122 EXPECT_EQ(2, copies); 1123 EXPECT_EQ(0, assigns); 1124 1125 copies = 0; 1126 assigns = 0; 1127 Bind(&VoidPolymorphic<CopyCounter>::Run) 1128 .Run(CopyCounter( 1129 DerivedCopyMoveCounter(&copies, &assigns, nullptr, nullptr))); 1130 EXPECT_EQ(2, copies); 1131 EXPECT_EQ(0, assigns); 1132 } 1133 1134 // Argument move-constructor usage for move-only parameters. 1135 // - Bound arguments passed by move are not copied. 1136 TEST_F(BindTest, ArgumentMoves) { 1137 int move_constructs = 0; 1138 int move_assigns = 0; 1139 1140 Bind(&VoidPolymorphic<const MoveCounter&>::Run, 1141 MoveCounter(&move_constructs, &move_assigns)); 1142 EXPECT_EQ(1, move_constructs); 1143 EXPECT_EQ(0, move_assigns); 1144 1145 // TODO(tzik): Support binding move-only type into a non-reference parameter 1146 // of a variant of Callback. 1147 1148 move_constructs = 0; 1149 move_assigns = 0; 1150 Bind(&VoidPolymorphic<MoveCounter>::Run) 1151 .Run(MoveCounter(&move_constructs, &move_assigns)); 1152 EXPECT_EQ(1, move_constructs); 1153 EXPECT_EQ(0, move_assigns); 1154 1155 move_constructs = 0; 1156 move_assigns = 0; 1157 Bind(&VoidPolymorphic<MoveCounter>::Run) 1158 .Run(MoveCounter(DerivedCopyMoveCounter( 1159 nullptr, nullptr, &move_constructs, &move_assigns))); 1160 EXPECT_EQ(2, move_constructs); 1161 EXPECT_EQ(0, move_assigns); 1162 } 1163 1164 // Argument constructor usage for non-reference movable-copyable 1165 // parameters. 1166 // - Bound arguments passed by move are not copied. 1167 // - Forwarded arguments are only copied once. 1168 // - Forwarded arguments with coercions are only copied once and moved once. 1169 TEST_F(BindTest, ArgumentCopiesAndMoves) { 1170 int copies = 0; 1171 int assigns = 0; 1172 int move_constructs = 0; 1173 int move_assigns = 0; 1174 1175 CopyMoveCounter counter(&copies, &assigns, &move_constructs, &move_assigns); 1176 Bind(&VoidPolymorphic<CopyMoveCounter>::Run, counter); 1177 EXPECT_EQ(1, copies); 1178 EXPECT_EQ(0, assigns); 1179 EXPECT_EQ(0, move_constructs); 1180 EXPECT_EQ(0, move_assigns); 1181 1182 copies = 0; 1183 assigns = 0; 1184 move_constructs = 0; 1185 move_assigns = 0; 1186 Bind(&VoidPolymorphic<CopyMoveCounter>::Run, 1187 CopyMoveCounter(&copies, &assigns, &move_constructs, &move_assigns)); 1188 EXPECT_EQ(0, copies); 1189 EXPECT_EQ(0, assigns); 1190 EXPECT_EQ(1, move_constructs); 1191 EXPECT_EQ(0, move_assigns); 1192 1193 copies = 0; 1194 assigns = 0; 1195 move_constructs = 0; 1196 move_assigns = 0; 1197 Bind(&VoidPolymorphic<CopyMoveCounter>::Run).Run(counter); 1198 EXPECT_EQ(1, copies); 1199 EXPECT_EQ(0, assigns); 1200 EXPECT_EQ(1, move_constructs); 1201 EXPECT_EQ(0, move_assigns); 1202 1203 copies = 0; 1204 assigns = 0; 1205 move_constructs = 0; 1206 move_assigns = 0; 1207 Bind(&VoidPolymorphic<CopyMoveCounter>::Run) 1208 .Run(CopyMoveCounter(&copies, &assigns, &move_constructs, &move_assigns)); 1209 EXPECT_EQ(0, copies); 1210 EXPECT_EQ(0, assigns); 1211 EXPECT_EQ(1, move_constructs); 1212 EXPECT_EQ(0, move_assigns); 1213 1214 DerivedCopyMoveCounter derived_counter(&copies, &assigns, &move_constructs, 1215 &move_assigns); 1216 copies = 0; 1217 assigns = 0; 1218 move_constructs = 0; 1219 move_assigns = 0; 1220 Bind(&VoidPolymorphic<CopyMoveCounter>::Run) 1221 .Run(CopyMoveCounter(derived_counter)); 1222 EXPECT_EQ(1, copies); 1223 EXPECT_EQ(0, assigns); 1224 EXPECT_EQ(1, move_constructs); 1225 EXPECT_EQ(0, move_assigns); 1226 1227 copies = 0; 1228 assigns = 0; 1229 move_constructs = 0; 1230 move_assigns = 0; 1231 Bind(&VoidPolymorphic<CopyMoveCounter>::Run) 1232 .Run(CopyMoveCounter(DerivedCopyMoveCounter( 1233 &copies, &assigns, &move_constructs, &move_assigns))); 1234 EXPECT_EQ(0, copies); 1235 EXPECT_EQ(0, assigns); 1236 EXPECT_EQ(2, move_constructs); 1237 EXPECT_EQ(0, move_assigns); 1238 } 1239 1240 TEST_F(BindTest, CapturelessLambda) { 1241 EXPECT_FALSE(internal::IsConvertibleToRunType<void>::value); 1242 EXPECT_FALSE(internal::IsConvertibleToRunType<int>::value); 1243 EXPECT_FALSE(internal::IsConvertibleToRunType<void(*)()>::value); 1244 EXPECT_FALSE(internal::IsConvertibleToRunType<void(NoRef::*)()>::value); 1245 1246 auto f = []() {}; 1247 EXPECT_TRUE(internal::IsConvertibleToRunType<decltype(f)>::value); 1248 1249 int i = 0; 1250 auto g = [i]() { (void)i; }; 1251 EXPECT_FALSE(internal::IsConvertibleToRunType<decltype(g)>::value); 1252 1253 auto h = [](int, double) { return 'k'; }; 1254 EXPECT_TRUE((std::is_same< 1255 char(int, double), 1256 internal::ExtractCallableRunType<decltype(h)>>::value)); 1257 1258 EXPECT_EQ(42, Bind([] { return 42; }).Run()); 1259 EXPECT_EQ(42, Bind([](int i) { return i * 7; }, 6).Run()); 1260 1261 int x = 1; 1262 base::Callback<void(int)> cb = 1263 Bind([](int* x, int i) { *x *= i; }, Unretained(&x)); 1264 cb.Run(6); 1265 EXPECT_EQ(6, x); 1266 cb.Run(7); 1267 EXPECT_EQ(42, x); 1268 } 1269 1270 TEST_F(BindTest, Cancellation) { 1271 EXPECT_CALL(no_ref_, VoidMethodWithIntArg(_)).Times(2); 1272 1273 WeakPtrFactory<NoRef> weak_factory(&no_ref_); 1274 RepeatingCallback<void(int)> cb = 1275 BindRepeating(&NoRef::VoidMethodWithIntArg, weak_factory.GetWeakPtr()); 1276 RepeatingClosure cb2 = BindRepeating(cb, 8); 1277 OnceClosure cb3 = BindOnce(cb, 8); 1278 1279 OnceCallback<void(int)> cb4 = 1280 BindOnce(&NoRef::VoidMethodWithIntArg, weak_factory.GetWeakPtr()); 1281 EXPECT_FALSE(cb4.IsCancelled()); 1282 1283 OnceClosure cb5 = BindOnce(std::move(cb4), 8); 1284 1285 EXPECT_FALSE(cb.IsCancelled()); 1286 EXPECT_FALSE(cb2.IsCancelled()); 1287 EXPECT_FALSE(cb3.IsCancelled()); 1288 EXPECT_FALSE(cb5.IsCancelled()); 1289 1290 cb.Run(6); 1291 cb2.Run(); 1292 1293 weak_factory.InvalidateWeakPtrs(); 1294 1295 EXPECT_TRUE(cb.IsCancelled()); 1296 EXPECT_TRUE(cb2.IsCancelled()); 1297 EXPECT_TRUE(cb3.IsCancelled()); 1298 EXPECT_TRUE(cb5.IsCancelled()); 1299 1300 cb.Run(6); 1301 cb2.Run(); 1302 std::move(cb3).Run(); 1303 std::move(cb5).Run(); 1304 } 1305 1306 TEST_F(BindTest, OnceCallback) { 1307 // Check if Callback variants have declarations of conversions as expected. 1308 // Copy constructor and assignment of RepeatingCallback. 1309 static_assert(std::is_constructible< 1310 RepeatingClosure, const RepeatingClosure&>::value, 1311 "RepeatingClosure should be copyable."); 1312 static_assert( 1313 std::is_assignable<RepeatingClosure, const RepeatingClosure&>::value, 1314 "RepeatingClosure should be copy-assignable."); 1315 1316 // Move constructor and assignment of RepeatingCallback. 1317 static_assert(std::is_constructible< 1318 RepeatingClosure, RepeatingClosure&&>::value, 1319 "RepeatingClosure should be movable."); 1320 static_assert(std::is_assignable<RepeatingClosure, RepeatingClosure&&>::value, 1321 "RepeatingClosure should be move-assignable"); 1322 1323 // Conversions from OnceCallback to RepeatingCallback. 1324 static_assert(!std::is_constructible< 1325 RepeatingClosure, const OnceClosure&>::value, 1326 "OnceClosure should not be convertible to RepeatingClosure."); 1327 static_assert( 1328 !std::is_assignable<RepeatingClosure, const OnceClosure&>::value, 1329 "OnceClosure should not be convertible to RepeatingClosure."); 1330 1331 // Destructive conversions from OnceCallback to RepeatingCallback. 1332 static_assert(!std::is_constructible< 1333 RepeatingClosure, OnceClosure&&>::value, 1334 "OnceClosure should not be convertible to RepeatingClosure."); 1335 static_assert(!std::is_assignable<RepeatingClosure, OnceClosure&&>::value, 1336 "OnceClosure should not be convertible to RepeatingClosure."); 1337 1338 // Copy constructor and assignment of OnceCallback. 1339 static_assert(!std::is_constructible< 1340 OnceClosure, const OnceClosure&>::value, 1341 "OnceClosure should not be copyable."); 1342 static_assert(!std::is_assignable<OnceClosure, const OnceClosure&>::value, 1343 "OnceClosure should not be copy-assignable"); 1344 1345 // Move constructor and assignment of OnceCallback. 1346 static_assert(std::is_constructible< 1347 OnceClosure, OnceClosure&&>::value, 1348 "OnceClosure should be movable."); 1349 static_assert(std::is_assignable<OnceClosure, OnceClosure&&>::value, 1350 "OnceClosure should be move-assignable."); 1351 1352 // Conversions from RepeatingCallback to OnceCallback. 1353 static_assert(std::is_constructible< 1354 OnceClosure, const RepeatingClosure&>::value, 1355 "RepeatingClosure should be convertible to OnceClosure."); 1356 static_assert(std::is_assignable<OnceClosure, const RepeatingClosure&>::value, 1357 "RepeatingClosure should be convertible to OnceClosure."); 1358 1359 // Destructive conversions from RepeatingCallback to OnceCallback. 1360 static_assert(std::is_constructible< 1361 OnceClosure, RepeatingClosure&&>::value, 1362 "RepeatingClosure should be convertible to OnceClosure."); 1363 static_assert(std::is_assignable<OnceClosure, RepeatingClosure&&>::value, 1364 "RepeatingClosure should be covretible to OnceClosure."); 1365 1366 OnceClosure cb = BindOnce(&VoidPolymorphic<>::Run); 1367 std::move(cb).Run(); 1368 1369 // RepeatingCallback should be convertible to OnceCallback. 1370 OnceClosure cb2 = BindRepeating(&VoidPolymorphic<>::Run); 1371 std::move(cb2).Run(); 1372 1373 RepeatingClosure cb3 = BindRepeating(&VoidPolymorphic<>::Run); 1374 cb = cb3; 1375 std::move(cb).Run(); 1376 1377 cb = std::move(cb2); 1378 1379 OnceCallback<void(int)> cb4 = BindOnce( 1380 &VoidPolymorphic<std::unique_ptr<int>, int>::Run, MakeUnique<int>(0)); 1381 BindOnce(std::move(cb4), 1).Run(); 1382 } 1383 1384 // Callback construction and assignment tests. 1385 // - Construction from an InvokerStorageHolder should not cause ref/deref. 1386 // - Assignment from other callback should only cause one ref 1387 // 1388 // TODO(ajwong): Is there actually a way to test this? 1389 1390 #if defined(OS_WIN) 1391 int __fastcall FastCallFunc(int n) { 1392 return n; 1393 } 1394 1395 int __stdcall StdCallFunc(int n) { 1396 return n; 1397 } 1398 1399 // Windows specific calling convention support. 1400 // - Can bind a __fastcall function. 1401 // - Can bind a __stdcall function. 1402 TEST_F(BindTest, WindowsCallingConventions) { 1403 Callback<int()> fastcall_cb = Bind(&FastCallFunc, 1); 1404 EXPECT_EQ(1, fastcall_cb.Run()); 1405 1406 Callback<int()> stdcall_cb = Bind(&StdCallFunc, 2); 1407 EXPECT_EQ(2, stdcall_cb.Run()); 1408 } 1409 #endif 1410 1411 // Test null callbacks cause a DCHECK. 1412 TEST(BindDeathTest, NullCallback) { 1413 base::Callback<void(int)> null_cb; 1414 ASSERT_TRUE(null_cb.is_null()); 1415 EXPECT_DCHECK_DEATH(base::Bind(null_cb, 42)); 1416 } 1417 1418 } // namespace 1419 } // namespace base 1420