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 #ifndef MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ | 5 #ifndef MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ |
6 #define MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ | 6 #define MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ |
7 | 7 |
8 #include <queue> | 8 #include <queue> |
9 #include <unordered_map> | 9 #include <unordered_map> |
10 #include <unordered_set> | 10 #include <unordered_set> |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
75 | 75 |
76 // Closes a port. Use this in lieu of calling Node::ClosePort() directly, as | 76 // Closes a port. Use this in lieu of calling Node::ClosePort() directly, as |
77 // it ensures the port's observer has also been removed. | 77 // it ensures the port's observer has also been removed. |
78 void ClosePort(const ports::PortRef& port); | 78 void ClosePort(const ports::PortRef& port); |
79 | 79 |
80 // Sends a message on a port to its peer. If message send fails, |message| | 80 // Sends a message on a port to its peer. If message send fails, |message| |
81 // is left intact. Otherwise ownership is transferred and it's reset. | 81 // is left intact. Otherwise ownership is transferred and it's reset. |
82 int SendMessage(const ports::PortRef& port_ref, | 82 int SendMessage(const ports::PortRef& port_ref, |
83 scoped_ptr<PortsMessage>* message); | 83 scoped_ptr<PortsMessage>* message); |
84 | 84 |
85 // Reserves a local port |port| associated with |token|. A peer holding a copy | 85 using ReservePortCallback = base::Callback<void(const ports::PortRef& port)>; |
86 // of |token| can merge one of its own ports into this one. | |
87 void ReservePort(const std::string& token, const ports::PortRef& port); | |
88 | 86 |
89 // Merges a local port |port| into a port reserved by |token| in the parent. | 87 // Reserves a port associated with |token|. A peer may associate one of their |
90 void MergePortIntoParent(const std::string& token, | 88 // own ports with this one by sending us a RequestPortConnection message with |
91 const ports::PortRef& port); | 89 // the same token value. |
| 90 // |
| 91 // Note that the reservation is made synchronously. In order to avoid races, |
| 92 // reservations should be acquired before |token| is communicated to any |
| 93 // potential peer. |
| 94 // |
| 95 // |callback| must be runnable on any thread and will be run with a reference |
| 96 // to the new local port once connected. |
| 97 void ReservePort(const std::string& token, |
| 98 const ReservePortCallback& callback); |
| 99 |
| 100 // Eventually initializes a local port with a parent port peer identified by |
| 101 // |token|. The parent should also have |token| and should alrady have |
| 102 // reserved a port for it. |callback| must be runnable on any thread and will |
| 103 // be run if and when the local port is connected. |
| 104 void ConnectToParentPort(const ports::PortRef& local_port, |
| 105 const std::string& token, |
| 106 const base::Closure& callback); |
| 107 |
| 108 // Connects two reserved ports to each other. Useful when two independent |
| 109 // systems in the same (parent) process need to establish a port pair without |
| 110 // any direct knowledge of each other. |
| 111 void ConnectReservedPorts(const std::string& token1, |
| 112 const std::string& token2); |
| 113 |
| 114 // Connects a local port to a port on a remote node. Note that a connection to |
| 115 // the remote node need not be established yet. The port will be connected |
| 116 // ASAP, at which point |callback| will be run. |
| 117 void ConnectToRemotePort(const ports::PortRef& local_port, |
| 118 const ports::NodeName& remote_node_name, |
| 119 const ports::PortName& remote_port_name, |
| 120 const base::Closure& callback); |
92 | 121 |
93 // Creates a new shared buffer for use in the current process. | 122 // Creates a new shared buffer for use in the current process. |
94 scoped_refptr<PlatformSharedBuffer> CreateSharedBuffer(size_t num_bytes); | 123 scoped_refptr<PlatformSharedBuffer> CreateSharedBuffer(size_t num_bytes); |
95 | 124 |
96 // Request that the Node be shut down cleanly. This may take an arbitrarily | 125 // Request that the Node be shut down cleanly. This may take an arbitrarily |
97 // long time to complete, at which point |callback| will be called. | 126 // long time to complete, at which point |callback| will be called. |
98 // | 127 // |
99 // Note that while it is safe to continue using the NodeController's public | 128 // Note that while it is safe to continue using the NodeController's public |
100 // interface after requesting shutdown, you do so at your own risk and there | 129 // interface after requesting shutdown, you do so at your own risk and there |
101 // is NO guarantee that new messages will be sent or ports will complete | 130 // is NO guarantee that new messages will be sent or ports will complete |
102 // transfer. | 131 // transfer. |
103 void RequestShutdown(const base::Closure& callback); | 132 void RequestShutdown(const base::Closure& callback); |
104 | 133 |
105 private: | 134 private: |
106 friend Core; | 135 friend Core; |
107 | 136 |
108 using NodeMap = std::unordered_map<ports::NodeName, | 137 using NodeMap = std::unordered_map<ports::NodeName, |
109 scoped_refptr<NodeChannel>>; | 138 scoped_refptr<NodeChannel>>; |
110 using OutgoingMessageQueue = std::queue<Channel::MessagePtr>; | 139 using OutgoingMessageQueue = std::queue<Channel::MessagePtr>; |
111 | 140 |
| 141 // Tracks a pending token-based connection to a parent port. |
| 142 struct PendingPortRequest { |
| 143 PendingPortRequest(); |
| 144 ~PendingPortRequest(); |
| 145 |
| 146 std::string token; |
| 147 ports::PortRef local_port; |
| 148 base::Closure callback; |
| 149 }; |
| 150 |
| 151 // Tracks a reserved port. |
| 152 struct ReservedPort { |
| 153 ReservedPort(); |
| 154 ~ReservedPort(); |
| 155 |
| 156 ports::PortRef local_port; |
| 157 ReservePortCallback callback; |
| 158 }; |
| 159 |
| 160 // Tracks a pending connection to a remote port on any peer. |
| 161 struct PendingRemotePortConnection { |
| 162 PendingRemotePortConnection(); |
| 163 ~PendingRemotePortConnection(); |
| 164 |
| 165 ports::PortRef local_port; |
| 166 ports::NodeName remote_node_name; |
| 167 ports::PortName remote_port_name; |
| 168 base::Closure callback; |
| 169 }; |
| 170 |
112 void ConnectToChildOnIOThread(base::ProcessHandle process_handle, | 171 void ConnectToChildOnIOThread(base::ProcessHandle process_handle, |
113 ScopedPlatformHandle platform_handle); | 172 ScopedPlatformHandle platform_handle); |
114 void ConnectToParentOnIOThread(ScopedPlatformHandle platform_handle); | 173 void ConnectToParentOnIOThread(ScopedPlatformHandle platform_handle); |
| 174 void RequestParentPortConnectionOnIOThread(const ports::PortRef& local_port, |
| 175 const std::string& token, |
| 176 const base::Closure& callback); |
| 177 void ConnectToRemotePortOnIOThread( |
| 178 const PendingRemotePortConnection& connection); |
115 | 179 |
116 scoped_refptr<NodeChannel> GetPeerChannel(const ports::NodeName& name); | 180 scoped_refptr<NodeChannel> GetPeerChannel(const ports::NodeName& name); |
117 scoped_refptr<NodeChannel> GetParentChannel(); | 181 scoped_refptr<NodeChannel> GetParentChannel(); |
118 scoped_refptr<NodeChannel> GetBrokerChannel(); | 182 scoped_refptr<NodeChannel> GetBrokerChannel(); |
119 | 183 |
120 void AddPeer(const ports::NodeName& name, | 184 void AddPeer(const ports::NodeName& name, |
121 scoped_refptr<NodeChannel> channel, | 185 scoped_refptr<NodeChannel> channel, |
122 bool start_channel); | 186 bool start_channel); |
123 void DropPeer(const ports::NodeName& name); | 187 void DropPeer(const ports::NodeName& name); |
124 void SendPeerMessage(const ports::NodeName& name, | 188 void SendPeerMessage(const ports::NodeName& name, |
(...skipping 19 matching lines...) Expand all Loading... |
144 void OnAddBrokerClient(const ports::NodeName& from_node, | 208 void OnAddBrokerClient(const ports::NodeName& from_node, |
145 const ports::NodeName& client_name, | 209 const ports::NodeName& client_name, |
146 ScopedPlatformHandle process_handle) override; | 210 ScopedPlatformHandle process_handle) override; |
147 void OnBrokerClientAdded(const ports::NodeName& from_node, | 211 void OnBrokerClientAdded(const ports::NodeName& from_node, |
148 const ports::NodeName& client_name, | 212 const ports::NodeName& client_name, |
149 ScopedPlatformHandle broker_channel) override; | 213 ScopedPlatformHandle broker_channel) override; |
150 void OnAcceptBrokerClient(const ports::NodeName& from_node, | 214 void OnAcceptBrokerClient(const ports::NodeName& from_node, |
151 const ports::NodeName& broker_name, | 215 const ports::NodeName& broker_name, |
152 ScopedPlatformHandle broker_channel) override; | 216 ScopedPlatformHandle broker_channel) override; |
153 void OnPortsMessage(Channel::MessagePtr message) override; | 217 void OnPortsMessage(Channel::MessagePtr message) override; |
154 void OnRequestPortMerge(const ports::NodeName& from_node, | 218 void OnRequestPortConnection(const ports::NodeName& from_node, |
155 const ports::PortName& connector_port_name, | 219 const ports::PortName& connector_port_name, |
156 const std::string& token) override; | 220 const std::string& token) override; |
| 221 void OnConnectToPort(const ports::NodeName& from_node, |
| 222 const ports::PortName& connector_port_name, |
| 223 const ports::PortName& connectee_port_name) override; |
157 void OnRequestIntroduction(const ports::NodeName& from_node, | 224 void OnRequestIntroduction(const ports::NodeName& from_node, |
158 const ports::NodeName& name) override; | 225 const ports::NodeName& name) override; |
159 void OnIntroduce(const ports::NodeName& from_node, | 226 void OnIntroduce(const ports::NodeName& from_node, |
160 const ports::NodeName& name, | 227 const ports::NodeName& name, |
161 ScopedPlatformHandle channel_handle) override; | 228 ScopedPlatformHandle channel_handle) override; |
162 #if defined(OS_WIN) | 229 #if defined(OS_WIN) |
163 void OnRelayPortsMessage(const ports::NodeName& from_node, | 230 void OnRelayPortsMessage(const ports::NodeName& from_node, |
164 base::ProcessHandle from_process, | 231 base::ProcessHandle from_process, |
165 const ports::NodeName& destination, | 232 const ports::NodeName& destination, |
166 Channel::MessagePtr message) override; | 233 Channel::MessagePtr message) override; |
(...skipping 23 matching lines...) Expand all Loading... |
190 NodeMap peers_; | 257 NodeMap peers_; |
191 | 258 |
192 // Outgoing message queues for peers we've heard of but can't yet talk to. | 259 // Outgoing message queues for peers we've heard of but can't yet talk to. |
193 std::unordered_map<ports::NodeName, OutgoingMessageQueue> | 260 std::unordered_map<ports::NodeName, OutgoingMessageQueue> |
194 pending_peer_messages_; | 261 pending_peer_messages_; |
195 | 262 |
196 // Guards |reserved_ports_|. | 263 // Guards |reserved_ports_|. |
197 base::Lock reserved_ports_lock_; | 264 base::Lock reserved_ports_lock_; |
198 | 265 |
199 // Ports reserved by token. | 266 // Ports reserved by token. |
200 base::hash_map<std::string, ports::PortRef> reserved_ports_; | 267 base::hash_map<std::string, ReservedPort> reserved_ports_; |
201 | |
202 // Guards |pending_port_merges_|. | |
203 base::Lock pending_port_merges_lock_; | |
204 | |
205 // A set of port merge requests awaiting parent connection. | |
206 std::vector<std::pair<std::string, ports::PortRef>> pending_port_merges_; | |
207 | 268 |
208 // Guards |parent_name_| and |bootstrap_parent_channel_|. | 269 // Guards |parent_name_| and |bootstrap_parent_channel_|. |
209 base::Lock parent_lock_; | 270 base::Lock parent_lock_; |
210 | 271 |
211 // The name of our parent node, if any. | 272 // The name of our parent node, if any. |
212 ports::NodeName parent_name_; | 273 ports::NodeName parent_name_; |
213 | 274 |
214 // A temporary reference to the parent channel before we know their name. | 275 // A temporary reference to the parent channel before we know their name. |
215 scoped_refptr<NodeChannel> bootstrap_parent_channel_; | 276 scoped_refptr<NodeChannel> bootstrap_parent_channel_; |
216 | 277 |
(...skipping 22 matching lines...) Expand all Loading... |
239 // begin polling the Node to see if clean shutdown is possible any time the | 300 // begin polling the Node to see if clean shutdown is possible any time the |
240 // Node's state is modified by the controller. | 301 // Node's state is modified by the controller. |
241 base::Closure shutdown_callback_; | 302 base::Closure shutdown_callback_; |
242 | 303 |
243 // All other fields below must only be accessed on the I/O thread, i.e., the | 304 // All other fields below must only be accessed on the I/O thread, i.e., the |
244 // thread on which core_->io_task_runner() runs tasks. | 305 // thread on which core_->io_task_runner() runs tasks. |
245 | 306 |
246 // Channels to children during handshake. | 307 // Channels to children during handshake. |
247 NodeMap pending_children_; | 308 NodeMap pending_children_; |
248 | 309 |
| 310 // Port connection requests which have been deferred until we have a parent. |
| 311 std::vector<PendingPortRequest> pending_port_requests_; |
| 312 |
| 313 // Port connection requests awaiting a response from the parent. |
| 314 std::unordered_map<ports::PortName, base::Closure> |
| 315 pending_parent_port_connections_; |
| 316 |
| 317 // Port connections pending the availability of a remote peer node. |
| 318 std::unordered_map<ports::NodeName, std::vector<PendingRemotePortConnection>> |
| 319 pending_remote_port_connections_; |
| 320 |
249 // Indicates whether this object should delete itself on IO thread shutdown. | 321 // Indicates whether this object should delete itself on IO thread shutdown. |
250 // Must only be accessed from the IO thread. | 322 // Must only be accessed from the IO thread. |
251 bool destroy_on_io_thread_shutdown_ = false; | 323 bool destroy_on_io_thread_shutdown_ = false; |
252 | 324 |
253 #if defined(OS_POSIX) | 325 #if defined(OS_POSIX) |
254 // Broker for sync shared buffer creation (posix-only) in children. | 326 // Broker for sync shared buffer creation (posix-only) in children. |
255 scoped_ptr<Broker> broker_; | 327 scoped_ptr<Broker> broker_; |
256 #endif | 328 #endif |
257 | 329 |
258 DISALLOW_COPY_AND_ASSIGN(NodeController); | 330 DISALLOW_COPY_AND_ASSIGN(NodeController); |
259 }; | 331 }; |
260 | 332 |
261 } // namespace edk | 333 } // namespace edk |
262 } // namespace mojo | 334 } // namespace mojo |
263 | 335 |
264 #endif // MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ | 336 #endif // MOJO_EDK_SYSTEM_NODE_CONTROLLER_H_ |
OLD | NEW |