Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 // Note: This file tests both binding.h (mojo::Binding) and strong_binding.h | 5 // Note: This file tests both binding.h (mojo::Binding) and strong_binding.h |
| 6 // (mojo::StrongBinding). | 6 // (mojo::StrongBinding). |
| 7 | 7 |
| 8 #include "mojo/public/cpp/bindings/binding.h" | 8 #include "mojo/public/cpp/bindings/binding.h" |
| 9 | 9 |
| 10 #include <stdint.h> | 10 #include <stdint.h> |
| (...skipping 416 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 427 // StrongBindingTest ----------------------------------------------------------- | 427 // StrongBindingTest ----------------------------------------------------------- |
| 428 | 428 |
| 429 using StrongBindingTest = BindingTestBase; | 429 using StrongBindingTest = BindingTestBase; |
| 430 | 430 |
| 431 // Tests that destroying a mojo::StrongBinding closes the bound message pipe | 431 // Tests that destroying a mojo::StrongBinding closes the bound message pipe |
| 432 // handle but does *not* destroy the implementation object. | 432 // handle but does *not* destroy the implementation object. |
| 433 TEST_F(StrongBindingTest, DestroyClosesMessagePipe) { | 433 TEST_F(StrongBindingTest, DestroyClosesMessagePipe) { |
| 434 base::RunLoop run_loop; | 434 base::RunLoop run_loop; |
| 435 bool encountered_error = false; | 435 bool encountered_error = false; |
| 436 bool was_deleted = false; | 436 bool was_deleted = false; |
| 437 ServiceImpl impl(&was_deleted); | |
| 438 sample::ServicePtr ptr; | 437 sample::ServicePtr ptr; |
| 439 auto request = GetProxy(&ptr); | 438 auto request = GetProxy(&ptr); |
| 440 ptr.set_connection_error_handler( | 439 ptr.set_connection_error_handler( |
| 441 SetFlagAndRunClosure(&encountered_error, run_loop.QuitClosure())); | 440 SetFlagAndRunClosure(&encountered_error, run_loop.QuitClosure())); |
| 442 bool called = false; | 441 bool called = false; |
| 443 base::RunLoop run_loop2; | 442 base::RunLoop run_loop2; |
| 444 { | 443 |
| 445 StrongBinding<sample::Service> binding(&impl, std::move(request)); | 444 auto binding = MakeStrongBinding( |
| 446 ptr->Frobinate(nullptr, sample::Service::BazOptions::REGULAR, nullptr, | 445 base::MakeUnique<ServiceImpl>(&was_deleted), std::move(request)); |
| 447 SetFlagAndRunClosure<int32_t>(&called, | 446 ptr->Frobinate(nullptr, sample::Service::BazOptions::REGULAR, nullptr, |
| 448 run_loop2.QuitClosure())); | 447 SetFlagAndRunClosure<int32_t>(&called, |
| 449 run_loop2.Run(); | 448 run_loop2.QuitClosure())); |
| 450 EXPECT_TRUE(called); | 449 run_loop2.Run(); |
| 451 EXPECT_FALSE(encountered_error); | 450 EXPECT_TRUE(called); |
| 452 } | 451 EXPECT_FALSE(encountered_error); |
| 453 // Now that the StrongBinding is out of scope we should detect an error on the | 452 binding->Close(); |
| 454 // other end of the pipe. | 453 |
| 454 // Now that the StrongBinding is closed we should detect an error on the other | |
| 455 // end of the pipe. | |
| 455 run_loop.Run(); | 456 run_loop.Run(); |
| 456 EXPECT_TRUE(encountered_error); | 457 EXPECT_TRUE(encountered_error); |
| 457 // But destroying the StrongBinding doesn't destroy the object. | 458 |
| 458 ASSERT_FALSE(was_deleted); | 459 // Destroying the StrongBinding also destroys the impl. |
| 460 ASSERT_TRUE(was_deleted); | |
| 459 } | 461 } |
| 460 | 462 |
| 461 class ServiceImplWithStrongBinding : public ServiceImpl { | |
| 462 public: | |
| 463 ServiceImplWithStrongBinding(bool* was_deleted, | |
| 464 InterfaceRequest<sample::Service> request) | |
| 465 : ServiceImpl(was_deleted), binding_(this, std::move(request)) {} | |
| 466 | |
| 467 StrongBinding<sample::Service>& binding() { return binding_; } | |
| 468 | |
| 469 private: | |
| 470 StrongBinding<sample::Service> binding_; | |
| 471 | |
| 472 DISALLOW_COPY_AND_ASSIGN(ServiceImplWithStrongBinding); | |
| 473 }; | |
| 474 | |
| 475 // Tests the typical case, where the implementation object owns the | 463 // Tests the typical case, where the implementation object owns the |
| 476 // StrongBinding (and should be destroyed on connection error). | 464 // StrongBinding (and should be destroyed on connection error). |
| 477 TEST_F(StrongBindingTest, ConnectionErrorDestroysImpl) { | 465 TEST_F(StrongBindingTest, ConnectionErrorDestroysImpl) { |
| 478 sample::ServicePtr ptr; | 466 sample::ServicePtr ptr; |
| 479 bool was_deleted = false; | 467 bool was_deleted = false; |
| 480 // Will delete itself. | 468 // Will delete itself. |
| 481 base::RunLoop run_loop; | 469 base::RunLoop run_loop; |
| 482 new ServiceImplWithBinding(&was_deleted, run_loop.QuitClosure(), | 470 new ServiceImplWithBinding(&was_deleted, run_loop.QuitClosure(), |
| 483 GetProxy(&ptr)); | 471 GetProxy(&ptr)); |
| 484 | 472 |
| 485 base::RunLoop().RunUntilIdle(); | 473 base::RunLoop().RunUntilIdle(); |
| 486 EXPECT_FALSE(was_deleted); | 474 EXPECT_FALSE(was_deleted); |
| 487 | 475 |
| 488 ptr.reset(); | 476 ptr.reset(); |
| 489 EXPECT_FALSE(was_deleted); | 477 EXPECT_FALSE(was_deleted); |
| 490 run_loop.Run(); | 478 run_loop.Run(); |
| 491 EXPECT_TRUE(was_deleted); | 479 EXPECT_TRUE(was_deleted); |
| 492 } | 480 } |
| 493 | 481 |
| 494 // Tests that even when the implementation object owns the StrongBinding, that | |
|
yzshen1
2016/09/09 16:21:30
This pattern seems pretty weird. +1 that StrongBin
| |
| 495 // the implementation can still be deleted (which should result in the message | |
| 496 // pipe being closed). Also checks that the connection error handler doesn't get | |
| 497 // called. | |
| 498 TEST_F(StrongBindingTest, ExplicitDeleteImpl) { | |
| 499 bool ptr_error_handler_called = false; | |
| 500 sample::ServicePtr ptr; | |
| 501 auto request = GetProxy(&ptr); | |
| 502 base::RunLoop run_loop; | |
| 503 ptr.set_connection_error_handler( | |
| 504 SetFlagAndRunClosure(&ptr_error_handler_called, run_loop.QuitClosure())); | |
| 505 bool was_deleted = false; | |
| 506 ServiceImplWithStrongBinding* impl = | |
| 507 new ServiceImplWithStrongBinding(&was_deleted, std::move(request)); | |
| 508 bool binding_error_handler_called = false; | |
| 509 impl->binding().set_connection_error_handler( | |
| 510 SetFlagAndRunClosure(&binding_error_handler_called)); | |
| 511 | |
| 512 base::RunLoop().RunUntilIdle(); | |
| 513 EXPECT_FALSE(ptr_error_handler_called); | |
| 514 EXPECT_FALSE(was_deleted); | |
| 515 | |
| 516 delete impl; | |
| 517 EXPECT_FALSE(ptr_error_handler_called); | |
| 518 EXPECT_TRUE(was_deleted); | |
| 519 was_deleted = false; // It shouldn't be double-deleted! | |
| 520 run_loop.Run(); | |
| 521 EXPECT_TRUE(ptr_error_handler_called); | |
| 522 EXPECT_FALSE(was_deleted); | |
| 523 | |
| 524 EXPECT_FALSE(binding_error_handler_called); | |
| 525 } | |
| 526 | |
| 527 TEST_F(StrongBindingTest, FlushForTesting) { | 482 TEST_F(StrongBindingTest, FlushForTesting) { |
| 528 bool called = false; | 483 bool called = false; |
| 529 bool was_deleted = false; | 484 bool was_deleted = false; |
| 530 sample::ServicePtr ptr; | 485 sample::ServicePtr ptr; |
| 531 auto request = GetProxy(&ptr); | 486 auto request = GetProxy(&ptr); |
| 532 StrongBinding<sample::Service> binding(new ServiceImpl(&was_deleted), | 487 auto binding = MakeStrongBinding(base::MakeUnique<ServiceImpl>(&was_deleted), |
| 533 std::move(request)); | 488 std::move(request)); |
| 534 binding.set_connection_error_handler(base::Bind(&Fail)); | 489 binding->set_connection_error_handler(base::Bind(&Fail)); |
| 535 | 490 |
| 536 ptr->Frobinate(nullptr, sample::Service::BazOptions::REGULAR, nullptr, | 491 ptr->Frobinate(nullptr, sample::Service::BazOptions::REGULAR, nullptr, |
| 537 SetFlagAndRunClosure<int32_t>(&called)); | 492 SetFlagAndRunClosure<int32_t>(&called)); |
| 538 EXPECT_FALSE(called); | 493 EXPECT_FALSE(called); |
| 539 // Because the flush is sent from the binding, it only guarantees that the | 494 // Because the flush is sent from the binding, it only guarantees that the |
| 540 // request has been received, not the response. The second flush waits for the | 495 // request has been received, not the response. The second flush waits for the |
| 541 // response to be received. | 496 // response to be received. |
| 542 binding.FlushForTesting(); | 497 ASSERT_TRUE(binding); |
| 543 binding.FlushForTesting(); | 498 binding->FlushForTesting(); |
| 499 ASSERT_TRUE(binding); | |
| 500 binding->FlushForTesting(); | |
| 544 EXPECT_TRUE(called); | 501 EXPECT_TRUE(called); |
| 545 EXPECT_FALSE(was_deleted); | 502 EXPECT_FALSE(was_deleted); |
| 546 ptr.reset(); | 503 ptr.reset(); |
| 547 binding.set_connection_error_handler(base::Closure()); | 504 ASSERT_TRUE(binding); |
| 548 binding.FlushForTesting(); | 505 binding->set_connection_error_handler(base::Closure()); |
| 506 binding->FlushForTesting(); | |
| 549 EXPECT_TRUE(was_deleted); | 507 EXPECT_TRUE(was_deleted); |
| 550 } | 508 } |
| 551 | 509 |
| 552 TEST_F(StrongBindingTest, FlushForTestingWithClosedPeer) { | 510 TEST_F(StrongBindingTest, FlushForTestingWithClosedPeer) { |
| 553 bool called = false; | 511 bool called = false; |
| 554 bool was_deleted = false; | 512 bool was_deleted = false; |
| 555 sample::ServicePtr ptr; | 513 sample::ServicePtr ptr; |
| 556 auto request = GetProxy(&ptr); | 514 auto request = GetProxy(&ptr); |
| 557 StrongBinding<sample::Service> binding(new ServiceImpl(&was_deleted), | 515 auto binding = MakeStrongBinding(base::MakeUnique<ServiceImpl>(&was_deleted), |
| 558 std::move(request)); | 516 std::move(request)); |
| 559 binding.set_connection_error_handler(SetFlagAndRunClosure(&called)); | 517 binding->set_connection_error_handler(SetFlagAndRunClosure(&called)); |
| 560 ptr.reset(); | 518 ptr.reset(); |
| 561 | 519 |
| 562 EXPECT_FALSE(called); | 520 EXPECT_FALSE(called); |
| 563 EXPECT_FALSE(was_deleted); | 521 EXPECT_FALSE(was_deleted); |
| 564 binding.FlushForTesting(); | 522 ASSERT_TRUE(binding); |
| 523 binding->FlushForTesting(); | |
| 565 EXPECT_TRUE(called); | 524 EXPECT_TRUE(called); |
| 566 EXPECT_TRUE(was_deleted); | 525 EXPECT_TRUE(was_deleted); |
| 567 binding.FlushForTesting(); | 526 ASSERT_FALSE(binding); |
| 568 EXPECT_TRUE(was_deleted); | |
| 569 } | 527 } |
| 570 | 528 |
| 571 } // namespace | 529 } // namespace |
| 572 } // mojo | 530 } // mojo |
| OLD | NEW |