OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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/edk/system/remote_message_pipe_bootstrap.h" | 5 #include "mojo/edk/system/remote_message_pipe_bootstrap.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/bind_helpers.h" | 8 #include "base/bind_helpers.h" |
9 #include "base/macros.h" | 9 #include "base/macros.h" |
10 #include "base/thread_task_runner_handle.h" | 10 #include "base/thread_task_runner_handle.h" |
(...skipping 13 matching lines...) Expand all Loading... |
24 // The port name of the sender's local bootstrap port. | 24 // The port name of the sender's local bootstrap port. |
25 ports::PortName port_name; | 25 ports::PortName port_name; |
26 }; | 26 }; |
27 | 27 |
28 } // namespace | 28 } // namespace |
29 | 29 |
30 // static | 30 // static |
31 void RemoteMessagePipeBootstrap::Create( | 31 void RemoteMessagePipeBootstrap::Create( |
32 NodeController* node_controller, | 32 NodeController* node_controller, |
33 ScopedPlatformHandle platform_handle, | 33 ScopedPlatformHandle platform_handle, |
34 const ports::PortRef& port) { | 34 const ports::PortRef& port, |
| 35 const base::Closure& callback) { |
35 if (node_controller->io_task_runner()->RunsTasksOnCurrentThread()) { | 36 if (node_controller->io_task_runner()->RunsTasksOnCurrentThread()) { |
36 // Owns itself. | 37 // Owns itself. |
37 new RemoteMessagePipeBootstrap( | 38 new RemoteMessagePipeBootstrap(node_controller, std::move(platform_handle), |
38 node_controller, std::move(platform_handle), port); | 39 port, callback); |
39 } else { | 40 } else { |
40 node_controller->io_task_runner()->PostTask( | 41 node_controller->io_task_runner()->PostTask( |
41 FROM_HERE, | 42 FROM_HERE, |
42 base::Bind(&RemoteMessagePipeBootstrap::Create, | 43 base::Bind(&RemoteMessagePipeBootstrap::Create, |
43 base::Unretained(node_controller), | 44 base::Unretained(node_controller), |
44 base::Passed(&platform_handle), port)); | 45 base::Passed(&platform_handle), port, callback)); |
45 } | 46 } |
46 } | 47 } |
47 | 48 |
48 RemoteMessagePipeBootstrap::~RemoteMessagePipeBootstrap() { | 49 RemoteMessagePipeBootstrap::~RemoteMessagePipeBootstrap() { |
49 DCHECK(io_task_runner_->RunsTasksOnCurrentThread()); | 50 DCHECK(io_task_runner_->RunsTasksOnCurrentThread()); |
50 base::MessageLoop::current()->RemoveDestructionObserver(this); | 51 base::MessageLoop::current()->RemoveDestructionObserver(this); |
51 if (channel_) | 52 if (channel_) |
52 channel_->ShutDown(); | 53 channel_->ShutDown(); |
53 } | 54 } |
54 | 55 |
55 RemoteMessagePipeBootstrap::RemoteMessagePipeBootstrap( | 56 RemoteMessagePipeBootstrap::RemoteMessagePipeBootstrap( |
56 NodeController* node_controller, | 57 NodeController* node_controller, |
57 ScopedPlatformHandle platform_handle, | 58 ScopedPlatformHandle platform_handle, |
58 const ports::PortRef& port) | 59 const ports::PortRef& port, |
| 60 const base::Closure& callback) |
59 : node_controller_(node_controller), | 61 : node_controller_(node_controller), |
60 local_port_(port), | 62 local_port_(port), |
| 63 callback_(callback), |
61 io_task_runner_(base::ThreadTaskRunnerHandle::Get()), | 64 io_task_runner_(base::ThreadTaskRunnerHandle::Get()), |
62 channel_(Channel::Create(this, std::move(platform_handle), | 65 channel_(Channel::Create(this, std::move(platform_handle), |
63 io_task_runner_)) { | 66 io_task_runner_)) { |
64 base::MessageLoop::current()->AddDestructionObserver(this); | 67 base::MessageLoop::current()->AddDestructionObserver(this); |
65 channel_->Start(); | 68 channel_->Start(); |
66 | 69 |
67 Channel::MessagePtr message(new Channel::Message(sizeof(BootstrapData), 0)); | 70 Channel::MessagePtr message(new Channel::Message(sizeof(BootstrapData), 0)); |
68 BootstrapData* data = static_cast<BootstrapData*>(message->mutable_payload()); | 71 BootstrapData* data = static_cast<BootstrapData*>(message->mutable_payload()); |
69 data->node_name = node_controller_->name(); | 72 data->node_name = node_controller_->name(); |
70 data->port_name = local_port_.name(); | 73 data->port_name = local_port_.name(); |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
109 return; | 112 return; |
110 } | 113 } |
111 | 114 |
112 if (payload_size != sizeof(BootstrapData)) { | 115 if (payload_size != sizeof(BootstrapData)) { |
113 DLOG(ERROR) << "Invalid bootstrap payload."; | 116 DLOG(ERROR) << "Invalid bootstrap payload."; |
114 ShutDown(); | 117 ShutDown(); |
115 return; | 118 return; |
116 } | 119 } |
117 | 120 |
118 peer_info_received_ = true; | 121 peer_info_received_ = true; |
119 | 122 node_controller_->ConnectToRemotePort( |
120 // We need to choose one side to initiate the port merge. It doesn't matter | 123 local_port_, data->node_name, data->port_name, callback_); |
121 // who does it as long as they don't both try. Simple solution: pick the one | |
122 // with the "smaller" port name. | |
123 if (local_port_.name() < data->port_name) { | |
124 node_controller_->node()->MergePorts(local_port_, data->node_name, | |
125 data->port_name); | |
126 } | |
127 | 124 |
128 // Send another ping to the other end to trigger shutdown. This may race with | 125 // Send another ping to the other end to trigger shutdown. This may race with |
129 // the other end sending its own ping, but it doesn't matter. Whoever wins | 126 // the other end sending its own ping, but it doesn't matter. Whoever wins |
130 // will cause the other end to tear down, and the ensuing channel error will | 127 // will cause the other end to tear down, and the ensuing channel error will |
131 // in turn clean up the remaining end. | 128 // in turn clean up the remaining end. |
132 | 129 |
133 Channel::MessagePtr message(new Channel::Message(0, 0)); | 130 Channel::MessagePtr message(new Channel::Message(0, 0)); |
134 channel_->Write(std::move(message)); | 131 channel_->Write(std::move(message)); |
135 } | 132 } |
136 | 133 |
137 void RemoteMessagePipeBootstrap::OnChannelError() { | 134 void RemoteMessagePipeBootstrap::OnChannelError() { |
138 DCHECK(io_task_runner_->RunsTasksOnCurrentThread()); | 135 DCHECK(io_task_runner_->RunsTasksOnCurrentThread()); |
139 ShutDown(); | 136 ShutDown(); |
140 } | 137 } |
141 | 138 |
142 void RemoteMessagePipeBootstrap::ShutDownNow() { | 139 void RemoteMessagePipeBootstrap::ShutDownNow() { |
143 delete this; | 140 delete this; |
144 } | 141 } |
145 | 142 |
146 } // namespace edk | 143 } // namespace edk |
147 } // namespace mojo | 144 } // namespace mojo |
OLD | NEW |