| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 "mojo/shell/shell.h" | 5 #include "mojo/shell/shell.h" |
| 6 | 6 |
| 7 #include <stdint.h> | 7 #include <stdint.h> |
| 8 | 8 |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 421 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 432 for (auto& runner : native_runners_) | 432 for (auto& runner : native_runners_) |
| 433 runner.reset(); | 433 runner.reset(); |
| 434 } | 434 } |
| 435 | 435 |
| 436 void Shell::SetInstanceQuitCallback( | 436 void Shell::SetInstanceQuitCallback( |
| 437 base::Callback<void(const Identity&)> callback) { | 437 base::Callback<void(const Identity&)> callback) { |
| 438 instance_quit_callback_ = callback; | 438 instance_quit_callback_ = callback; |
| 439 } | 439 } |
| 440 | 440 |
| 441 void Shell::Connect(scoped_ptr<ConnectParams> params) { | 441 void Shell::Connect(scoped_ptr<ConnectParams> params) { |
| 442 TRACE_EVENT_INSTANT1("mojo_shell", "Shell::Connect", | 442 Connect(std::move(params), nullptr); |
| 443 TRACE_EVENT_SCOPE_THREAD, "original_name", | |
| 444 params->target().name()); | |
| 445 DCHECK(IsValidName(params->target().name())); | |
| 446 DCHECK(base::IsValidGUID(params->target().user_id())); | |
| 447 DCHECK_NE(mojom::kInheritUserID, params->target().user_id()); | |
| 448 | |
| 449 // Connect to an existing matching instance, if possible. | |
| 450 if (ConnectToExistingInstance(¶ms)) | |
| 451 return; | |
| 452 | |
| 453 std::string name = params->target().name(); | |
| 454 shell_resolver_->ResolveMojoName( | |
| 455 name, | |
| 456 base::Bind(&Shell::OnGotResolvedName, | |
| 457 weak_ptr_factory_.GetWeakPtr(), base::Passed(¶ms))); | |
| 458 } | 443 } |
| 459 | 444 |
| 460 mojom::ShellClientRequest Shell::InitInstanceForEmbedder( | 445 mojom::ShellClientRequest Shell::InitInstanceForEmbedder( |
| 461 const std::string& name) { | 446 const std::string& name) { |
| 462 DCHECK(!embedder_instance_); | 447 scoped_ptr<ConnectParams> params(new ConnectParams); |
| 463 | 448 |
| 464 Identity target(name, mojom::kRootUserID); | 449 Identity embedder_identity(name, mojom::kRootUserID); |
| 465 DCHECK(!GetExistingInstance(target)); | 450 params->set_source(embedder_identity); |
| 451 params->set_target(embedder_identity); |
| 466 | 452 |
| 467 mojom::ShellClientPtr client; | 453 mojom::ShellClientPtr client; |
| 468 mojom::ShellClientRequest request = GetProxy(&client); | 454 mojom::ShellClientRequest request = GetProxy(&client); |
| 469 embedder_instance_ = | 455 Connect(std::move(params), std::move(client)); |
| 470 CreateInstance(target, GetPermissiveCapabilities(), std::move(client)); | |
| 471 DCHECK(embedder_instance_); | |
| 472 | 456 |
| 473 return request; | 457 return request; |
| 474 } | 458 } |
| 475 | 459 |
| 476 void Shell::SetLoaderForName(scoped_ptr<Loader> loader, | 460 void Shell::SetLoaderForName(scoped_ptr<Loader> loader, |
| 477 const std::string& name) { | 461 const std::string& name) { |
| 478 NameToLoaderMap::iterator it = name_to_loader_.find(name); | 462 NameToLoaderMap::iterator it = name_to_loader_.find(name); |
| 479 if (it != name_to_loader_.end()) | 463 if (it != name_to_loader_.end()) |
| 480 delete it->second; | 464 delete it->second; |
| 481 name_to_loader_[name] = loader.release(); | 465 name_to_loader_[name] = loader.release(); |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 528 int id = instance->id(); | 512 int id = instance->id(); |
| 529 delete it->second; | 513 delete it->second; |
| 530 identity_to_instance_.erase(it); | 514 identity_to_instance_.erase(it); |
| 531 instance_listeners_.ForAllPtrs([this, id](mojom::InstanceListener* listener) { | 515 instance_listeners_.ForAllPtrs([this, id](mojom::InstanceListener* listener) { |
| 532 listener->InstanceDestroyed(id); | 516 listener->InstanceDestroyed(id); |
| 533 }); | 517 }); |
| 534 if (!instance_quit_callback_.is_null()) | 518 if (!instance_quit_callback_.is_null()) |
| 535 instance_quit_callback_.Run(identity); | 519 instance_quit_callback_.Run(identity); |
| 536 } | 520 } |
| 537 | 521 |
| 522 void Shell::Connect(scoped_ptr<ConnectParams> params, |
| 523 mojom::ShellClientPtr client) { |
| 524 TRACE_EVENT_INSTANT1("mojo_shell", "Shell::Connect", |
| 525 TRACE_EVENT_SCOPE_THREAD, "original_name", |
| 526 params->target().name()); |
| 527 DCHECK(IsValidName(params->target().name())); |
| 528 DCHECK(base::IsValidGUID(params->target().user_id())); |
| 529 DCHECK_NE(mojom::kInheritUserID, params->target().user_id()); |
| 530 DCHECK(!client.is_bound() || !identity_to_instance_.count(params->target())); |
| 531 |
| 532 // Connect to an existing matching instance, if possible. |
| 533 if (!client.is_bound() && ConnectToExistingInstance(¶ms)) |
| 534 return; |
| 535 |
| 536 std::string name = params->target().name(); |
| 537 shell_resolver_->ResolveMojoName( |
| 538 name, |
| 539 base::Bind(&Shell::OnGotResolvedName, |
| 540 weak_ptr_factory_.GetWeakPtr(), base::Passed(¶ms), |
| 541 base::Passed(&client))); |
| 542 } |
| 543 |
| 538 Shell::Instance* Shell::GetExistingInstance(const Identity& identity) const { | 544 Shell::Instance* Shell::GetExistingInstance(const Identity& identity) const { |
| 539 const auto& it = identity_to_instance_.find(identity); | 545 const auto& it = identity_to_instance_.find(identity); |
| 540 return it != identity_to_instance_.end() ? it->second : nullptr; | 546 return it != identity_to_instance_.end() ? it->second : nullptr; |
| 541 } | 547 } |
| 542 | 548 |
| 543 Shell::Instance* Shell::GetExistingOrRootInstance( | 549 Shell::Instance* Shell::GetExistingOrRootInstance( |
| 544 const Identity& identity) const { | 550 const Identity& identity) const { |
| 545 Instance* instance = GetExistingInstance(identity); | 551 Instance* instance = GetExistingInstance(identity); |
| 546 if (!instance) { | 552 if (!instance) { |
| 547 Identity root_identity = identity; | 553 Identity root_identity = identity; |
| (...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 620 } | 626 } |
| 621 | 627 |
| 622 void Shell::OnShellClientFactoryLost(const Identity& which) { | 628 void Shell::OnShellClientFactoryLost(const Identity& which) { |
| 623 // Remove the mapping. | 629 // Remove the mapping. |
| 624 auto it = shell_client_factories_.find(which); | 630 auto it = shell_client_factories_.find(which); |
| 625 DCHECK(it != shell_client_factories_.end()); | 631 DCHECK(it != shell_client_factories_.end()); |
| 626 shell_client_factories_.erase(it); | 632 shell_client_factories_.erase(it); |
| 627 } | 633 } |
| 628 | 634 |
| 629 void Shell::OnGotResolvedName(scoped_ptr<ConnectParams> params, | 635 void Shell::OnGotResolvedName(scoped_ptr<ConnectParams> params, |
| 636 mojom::ShellClientPtr client, |
| 630 const String& resolved_name, | 637 const String& resolved_name, |
| 631 const String& resolved_instance, | 638 const String& resolved_instance, |
| 632 mojom::CapabilitySpecPtr capabilities_ptr, | 639 mojom::CapabilitySpecPtr capabilities_ptr, |
| 633 const String& file_url) { | 640 const String& file_url) { |
| 634 std::string instance_name = params->target().instance(); | 641 std::string instance_name = params->target().instance(); |
| 635 if (instance_name == GetNamePath(params->target().name()) && | 642 if (instance_name == GetNamePath(params->target().name()) && |
| 636 resolved_instance != GetNamePath(resolved_name)) { | 643 resolved_instance != GetNamePath(resolved_name)) { |
| 637 instance_name = resolved_instance; | 644 instance_name = resolved_instance; |
| 638 } | 645 } |
| 639 Identity target(params->target().name(), params->target().user_id(), | 646 Identity target(params->target().name(), params->target().user_id(), |
| 640 instance_name); | 647 instance_name); |
| 641 params->set_target(target); | 648 params->set_target(target); |
| 642 | 649 |
| 643 // It's possible that when this manifest request was issued, another one was | 650 // It's possible that when this manifest request was issued, another one was |
| 644 // already in-progress and completed by the time this one did, and so the | 651 // already in-progress and completed by the time this one did, and so the |
| 645 // requested application may already be running. | 652 // requested application may already be running. |
| 646 if (ConnectToExistingInstance(¶ms)) | 653 if (ConnectToExistingInstance(¶ms)) |
| 647 return; | 654 return; |
| 648 | 655 |
| 649 Identity source = params->source(); | 656 Identity source = params->source(); |
| 650 // |capabilities_ptr| can be null when there is no manifest, e.g. for URL | 657 // |capabilities_ptr| can be null when there is no manifest, e.g. for URL |
| 651 // types not resolvable by the resolver. | 658 // types not resolvable by the resolver. |
| 652 CapabilitySpec capabilities = GetPermissiveCapabilities(); | 659 CapabilitySpec capabilities = GetPermissiveCapabilities(); |
| 653 if (!capabilities_ptr.is_null()) | 660 if (!capabilities_ptr.is_null()) |
| 654 capabilities = capabilities_ptr.To<CapabilitySpec>(); | 661 capabilities = capabilities_ptr.To<CapabilitySpec>(); |
| 655 | 662 |
| 656 mojom::ClientProcessConnectionPtr client_process_connection = | 663 mojom::ClientProcessConnectionPtr client_process_connection = |
| 657 params->TakeClientProcessConnection(); | 664 params->TakeClientProcessConnection(); |
| 658 mojom::ShellClientPtr client; | 665 |
| 659 mojom::ShellClientRequest request = GetProxy(&client); | 666 mojom::ShellClientRequest request; |
| 667 if (!client.is_bound()) |
| 668 request = GetProxy(&client); |
| 669 |
| 660 Instance* instance = CreateInstance(target, capabilities, std::move(client)); | 670 Instance* instance = CreateInstance(target, capabilities, std::move(client)); |
| 661 instance->ConnectToClient(std::move(params)); | 671 instance->ConnectToClient(std::move(params)); |
| 662 | 672 |
| 663 if (LoadWithLoader(target, &request)) | 673 // If a ShellClientPtr was provided, there's no more work to do: someone |
| 674 // is already holding a corresponding ShellClientRequest. |
| 675 if (!request.is_pending()) |
| 676 return; |
| 677 |
| 678 if (client_process_connection.is_null() && LoadWithLoader(target, &request)) |
| 664 return; | 679 return; |
| 665 | 680 |
| 666 CHECK(!file_url.is_null() && !capabilities_ptr.is_null()); | 681 CHECK(!file_url.is_null() && !capabilities_ptr.is_null()); |
| 667 | 682 |
| 668 if (target.name() != resolved_name) { | 683 if (target.name() != resolved_name) { |
| 669 // In cases where a package alias is resolved, we have to use the instance | 684 // In cases where a package alias is resolved, we have to use the instance |
| 670 // from the original request rather than for the package itself, which will | 685 // from the original request rather than for the package itself, which will |
| 671 // always be the same. | 686 // always be the same. |
| 672 CreateShellClient( | 687 CreateShellClient( |
| 673 source, Identity(resolved_name, target.user_id(), instance_name), | 688 source, Identity(resolved_name, target.user_id(), instance_name), |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 705 for (auto it = native_runners_.begin(); it != native_runners_.end(); ++it) { | 720 for (auto it = native_runners_.begin(); it != native_runners_.end(); ++it) { |
| 706 if (it->get() == runner) { | 721 if (it->get() == runner) { |
| 707 native_runners_.erase(it); | 722 native_runners_.erase(it); |
| 708 return; | 723 return; |
| 709 } | 724 } |
| 710 } | 725 } |
| 711 } | 726 } |
| 712 | 727 |
| 713 } // namespace shell | 728 } // namespace shell |
| 714 } // namespace mojo | 729 } // namespace mojo |
| OLD | NEW |