Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(438)

Side by Side Diff: mojo/services/view_manager/view_manager_connection.cc

Issue 292283002: Finishes up setroots (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: cleanup Created 6 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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/services/view_manager/view_manager_connection.h" 5 #include "mojo/services/view_manager/view_manager_connection.h"
6 6
7 #include "base/stl_util.h" 7 #include "base/stl_util.h"
8 #include "mojo/public/cpp/bindings/allocation_scope.h" 8 #include "mojo/public/cpp/bindings/allocation_scope.h"
9 #include "mojo/services/view_manager/node.h" 9 #include "mojo/services/view_manager/node.h"
10 #include "mojo/services/view_manager/root_node_manager.h" 10 #include "mojo/services/view_manager/root_node_manager.h"
(...skipping 29 matching lines...) Expand all
40 ViewManagerConnection::~ViewManagerConnection() { 40 ViewManagerConnection::~ViewManagerConnection() {
41 // Delete any views we own. 41 // Delete any views we own.
42 while (!view_map_.empty()) { 42 while (!view_map_.empty()) {
43 bool result = DeleteViewImpl(this, view_map_.begin()->second->id()); 43 bool result = DeleteViewImpl(this, view_map_.begin()->second->id());
44 DCHECK(result); 44 DCHECK(result);
45 } 45 }
46 46
47 // We're about to destroy all our nodes. Detach any views from them. 47 // We're about to destroy all our nodes. Detach any views from them.
48 for (NodeMap::iterator i = node_map_.begin(); i != node_map_.end(); ++i) { 48 for (NodeMap::iterator i = node_map_.begin(); i != node_map_.end(); ++i) {
49 if (i->second->view()) { 49 if (i->second->view()) {
50 bool result = SetViewImpl(i->second->id(), ViewId()); 50 bool result = SetViewImpl(i->second, ViewId());
51 DCHECK(result); 51 DCHECK(result);
52 } 52 }
53 } 53 }
54 54
55 STLDeleteContainerPairSecondPointers(node_map_.begin(), node_map_.end()); 55 if (!node_map_.empty()) {
56 RootNodeManager::ScopedChange change(
57 this, root_node_manager_,
58 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, true);
59 while (!node_map_.empty()) {
60 Node* node = node_map_.begin()->second;
61 Node* parent = node->GetParent();
62 const NodeId node_id(node->id());
63 if (parent)
64 parent->Remove(node);
65 root_node_manager_->ProcessNodeDeleted(node_id);
66 node_map_.erase(NodeIdToTransportId(node_id));
67 }
68 }
69
56 root_node_manager_->RemoveConnection(this); 70 root_node_manager_->RemoveConnection(this);
57 } 71 }
58 72
59 void ViewManagerConnection::OnConnectionEstablished() { 73 void ViewManagerConnection::OnConnectionEstablished() {
60 DCHECK_EQ(0, id_); // Should only get OnConnectionEstablished() once. 74 DCHECK_EQ(0, id_); // Should only get OnConnectionEstablished() once.
61 id_ = root_node_manager_->GetAndAdvanceNextConnectionId(); 75 id_ = root_node_manager_->GetAndAdvanceNextConnectionId();
62 root_node_manager_->AddConnection(this); 76 root_node_manager_->AddConnection(this);
63 std::vector<const Node*> to_send; 77 std::vector<const Node*> to_send;
64 GetUnknownNodesFrom(root_node_manager_->root(), &to_send); 78 GetUnknownNodesFrom(root_node_manager_->root(), &to_send);
65 AllocationScope allocation_scope; 79 AllocationScope allocation_scope;
66 client()->OnConnectionEstablished( 80 client()->OnConnectionEstablished(
67 id_, 81 id_,
68 root_node_manager_->next_server_change_id(), 82 root_node_manager_->next_server_change_id(),
69 NodesToINodes(to_send)); 83 NodesToINodes(to_send));
70 } 84 }
71 85
72 const Node* ViewManagerConnection::GetNode(const NodeId& id) const { 86 const Node* ViewManagerConnection::GetNode(const NodeId& id) const {
73 if (id_ == id.connection_id) { 87 if (id_ == id.connection_id) {
74 NodeMap::const_iterator i = node_map_.find(id.node_id); 88 NodeMap::const_iterator i = node_map_.find(id.node_id);
75 return i == node_map_.end() ? NULL : i->second; 89 return i == node_map_.end() ? NULL : i->second;
76 } 90 }
77 return root_node_manager_->GetNode(id); 91 return root_node_manager_->GetNode(id);
78 } 92 }
79 93
80 View* ViewManagerConnection::GetView(const ViewId& id) { 94 const View* ViewManagerConnection::GetView(const ViewId& id) const {
81 if (id_ == id.connection_id) { 95 if (id_ == id.connection_id) {
82 ViewMap::const_iterator i = view_map_.find(id.view_id); 96 ViewMap::const_iterator i = view_map_.find(id.view_id);
83 return i == view_map_.end() ? NULL : i->second; 97 return i == view_map_.end() ? NULL : i->second;
84 } 98 }
85 return root_node_manager_->GetView(id); 99 return root_node_manager_->GetView(id);
86 } 100 }
87 101
88 void ViewManagerConnection::ProcessNodeHierarchyChanged( 102 void ViewManagerConnection::ProcessNodeHierarchyChanged(
89 const Node* node, 103 const Node* node,
90 const Node* new_parent, 104 const Node* new_parent,
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
142 ViewIdToTransportId(old_view->id()) : 0; 156 ViewIdToTransportId(old_view->id()) : 0;
143 client()->OnNodeViewReplaced(NodeIdToTransportId(node->id()), 157 client()->OnNodeViewReplaced(NodeIdToTransportId(node->id()),
144 new_view_id, old_view_id); 158 new_view_id, old_view_id);
145 } 159 }
146 160
147 void ViewManagerConnection::ProcessNodeDeleted( 161 void ViewManagerConnection::ProcessNodeDeleted(
148 const NodeId& node, 162 const NodeId& node,
149 TransportChangeId server_change_id, 163 TransportChangeId server_change_id,
150 bool originated_change) { 164 bool originated_change) {
151 const bool in_known = known_nodes_.erase(NodeIdToTransportId(node)) > 0; 165 const bool in_known = known_nodes_.erase(NodeIdToTransportId(node)) > 0;
166 const bool in_roots = roots_.erase(NodeIdToTransportId(node)) > 0;
167
168 if (in_roots && roots_.empty())
169 roots_.insert(NodeIdToTransportId(InvalidNodeId()));
152 170
153 if (originated_change) 171 if (originated_change)
154 return; 172 return;
155 173
156 if (in_known) { 174 if (in_known) {
157 client()->OnNodeDeleted(NodeIdToTransportId(node), server_change_id); 175 client()->OnNodeDeleted(NodeIdToTransportId(node), server_change_id);
158 } else if (root_node_manager_->IsProcessingChange()) { 176 } else if (root_node_manager_->IsProcessingChange()) {
159 client()->OnServerChangeIdAdvanced( 177 client()->OnServerChangeIdAdvanced(
160 root_node_manager_->next_server_change_id() + 1); 178 root_node_manager_->next_server_change_id() + 1);
161 } 179 }
162 } 180 }
163 181
164 void ViewManagerConnection::ProcessViewDeleted(const ViewId& view, 182 void ViewManagerConnection::ProcessViewDeleted(const ViewId& view,
165 bool originated_change) { 183 bool originated_change) {
166 if (originated_change) 184 if (originated_change)
167 return; 185 return;
168 client()->OnViewDeleted(ViewIdToTransportId(view)); 186 client()->OnViewDeleted(ViewIdToTransportId(view));
169 } 187 }
170 188
189 bool ViewManagerConnection::CanRemoveNodeFromParent(const Node* node) const {
190 if (!node)
191 return false;
192
193 const Node* parent = node->GetParent();
194 if (!parent)
195 return false;
196
197 // Always allow the remove if there are no roots. Otherwise the remove is
198 // allowed if the parent is a descendant of the roots, or the node and its
199 // parent were created by this connection. We explicitly disallow removal of
200 // the node from its parent if the parent isn't visible to this connection
201 // (not in roots).
202 return (roots_.empty() ||
203 (IsNodeDescendantOfRoots(parent) ||
204 (node->id().connection_id == id_ &&
205 parent->id().connection_id == id_)));
206 }
207
208 bool ViewManagerConnection::CanAddNode(const Node* parent,
209 const Node* child) const {
210 if (!parent || !child)
211 return false; // Both nodes must be valid.
212
213 if (child->GetParent() == parent || child->Contains(parent))
214 return false; // Would result in an invalid hierarchy.
215
216 if (roots_.empty())
217 return true; // No restriction if there are no roots.
218
219 if (!IsNodeDescendantOfRoots(parent) && parent->id().connection_id != id_)
220 return false; // |parent| is not visible to this connection.
221
222 // Allow the add if the child is already a descendant of the roots or was
223 // created by this connection.
224 return (IsNodeDescendantOfRoots(child) || child->id().connection_id == id_);
225 }
226
171 bool ViewManagerConnection::CanDeleteNode(const NodeId& node_id) const { 227 bool ViewManagerConnection::CanDeleteNode(const NodeId& node_id) const {
172 return node_id.connection_id == id_; 228 return node_id.connection_id == id_;
173 } 229 }
174 230
175 bool ViewManagerConnection::CanDeleteView(const ViewId& view_id) const { 231 bool ViewManagerConnection::CanDeleteView(const ViewId& view_id) const {
176 return view_id.connection_id == id_; 232 return view_id.connection_id == id_;
177 } 233 }
178 234
235 bool ViewManagerConnection::CanSetView(const Node* node,
236 const ViewId& view_id) const {
237 if (!node || !IsNodeDescendantOfRoots(node))
238 return false;
239
240 const View* view = GetView(view_id);
241 return (view && view_id.connection_id == id_) || view_id == ViewId();
242 }
243
244 bool ViewManagerConnection::CanGetNodeTree(const Node* node) const {
245 return node &&
246 (IsNodeDescendantOfRoots(node) || node->id().connection_id == id_);
247 }
248
179 bool ViewManagerConnection::DeleteNodeImpl(ViewManagerConnection* source, 249 bool ViewManagerConnection::DeleteNodeImpl(ViewManagerConnection* source,
180 const NodeId& node_id) { 250 const NodeId& node_id) {
181 DCHECK_EQ(node_id.connection_id, id_); 251 DCHECK_EQ(node_id.connection_id, id_);
182 Node* node = GetNode(node_id); 252 Node* node = GetNode(node_id);
183 if (!node) 253 if (!node)
184 return false; 254 return false;
185 RootNodeManager::ScopedChange change( 255 RootNodeManager::ScopedChange change(
186 source, root_node_manager_, 256 source, root_node_manager_,
187 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, true); 257 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, true);
188 if (node->GetParent()) 258 if (node->GetParent())
(...skipping 22 matching lines...) Expand all
211 view->node()->SetView(NULL); 281 view->node()->SetView(NULL);
212 view_map_.erase(view_id.view_id); 282 view_map_.erase(view_id.view_id);
213 // Make a copy of |view_id| as once we delete view |view_id| may no longer be 283 // Make a copy of |view_id| as once we delete view |view_id| may no longer be
214 // valid. 284 // valid.
215 const ViewId view_id_copy(view_id); 285 const ViewId view_id_copy(view_id);
216 delete view; 286 delete view;
217 root_node_manager_->ProcessViewDeleted(view_id_copy); 287 root_node_manager_->ProcessViewDeleted(view_id_copy);
218 return true; 288 return true;
219 } 289 }
220 290
221 bool ViewManagerConnection::SetViewImpl(const NodeId& node_id, 291 bool ViewManagerConnection::SetViewImpl(Node* node, const ViewId& view_id) {
222 const ViewId& view_id) { 292 DCHECK(node); // CanSetView() should have verified node exists.
223 Node* node = GetNode(node_id);
224 if (!node)
225 return false;
226 View* view = GetView(view_id); 293 View* view = GetView(view_id);
227 if (!view && view_id != ViewId())
228 return false;
229 RootNodeManager::ScopedChange change( 294 RootNodeManager::ScopedChange change(
230 this, root_node_manager_, 295 this, root_node_manager_,
231 RootNodeManager::CHANGE_TYPE_DONT_ADVANCE_SERVER_CHANGE_ID, false); 296 RootNodeManager::CHANGE_TYPE_DONT_ADVANCE_SERVER_CHANGE_ID, false);
232 node->SetView(view); 297 node->SetView(view);
233 return true; 298 return true;
234 } 299 }
235 300
236 void ViewManagerConnection::GetUnknownNodesFrom( 301 void ViewManagerConnection::GetUnknownNodesFrom(
237 const Node* node, 302 const Node* node,
238 std::vector<const Node*>* nodes) { 303 std::vector<const Node*>* nodes) {
(...skipping 14 matching lines...) Expand all
253 std::vector<const Node*> children = node->GetChildren(); 318 std::vector<const Node*> children = node->GetChildren();
254 for (size_t i = 0; i < children.size(); ++i) 319 for (size_t i = 0; i < children.size(); ++i)
255 RemoveFromKnown(children[i]); 320 RemoveFromKnown(children[i]);
256 } 321 }
257 322
258 bool ViewManagerConnection::IsNodeDescendantOfRoots(const Node* node) const { 323 bool ViewManagerConnection::IsNodeDescendantOfRoots(const Node* node) const {
259 if (roots_.empty()) 324 if (roots_.empty())
260 return true; 325 return true;
261 if (!node) 326 if (!node)
262 return false; 327 return false;
328 const TransportNodeId invalid_node_id =
329 NodeIdToTransportId(InvalidNodeId());
263 for (NodeIdSet::const_iterator i = roots_.begin(); i != roots_.end(); ++i) { 330 for (NodeIdSet::const_iterator i = roots_.begin(); i != roots_.end(); ++i) {
331 if (*i == invalid_node_id)
332 continue;
264 const Node* root = GetNode(NodeIdFromTransportId(*i)); 333 const Node* root = GetNode(NodeIdFromTransportId(*i));
265 DCHECK(root); 334 DCHECK(root);
266 if (root->Contains(node)) 335 if (root->Contains(node))
267 return true; 336 return true;
268 } 337 }
269 return false; 338 return false;
270 } 339 }
271 340
272 bool ViewManagerConnection::ShouldNotifyOnHierarchyChange( 341 bool ViewManagerConnection::ShouldNotifyOnHierarchyChange(
273 const Node* node, 342 const Node* node,
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
400 469
401 void ViewManagerConnection::AddNode( 470 void ViewManagerConnection::AddNode(
402 TransportNodeId parent_id, 471 TransportNodeId parent_id,
403 TransportNodeId child_id, 472 TransportNodeId child_id,
404 TransportChangeId server_change_id, 473 TransportChangeId server_change_id,
405 const Callback<void(bool)>& callback) { 474 const Callback<void(bool)>& callback) {
406 bool success = false; 475 bool success = false;
407 if (server_change_id == root_node_manager_->next_server_change_id()) { 476 if (server_change_id == root_node_manager_->next_server_change_id()) {
408 Node* parent = GetNode(NodeIdFromTransportId(parent_id)); 477 Node* parent = GetNode(NodeIdFromTransportId(parent_id));
409 Node* child = GetNode(NodeIdFromTransportId(child_id)); 478 Node* child = GetNode(NodeIdFromTransportId(child_id));
410 if (parent && child && child->GetParent() != parent && 479 if (CanAddNode(parent, child)) {
411 !child->window()->Contains(parent->window())) {
412 success = true; 480 success = true;
413 RootNodeManager::ScopedChange change( 481 RootNodeManager::ScopedChange change(
414 this, root_node_manager_, 482 this, root_node_manager_,
415 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, false); 483 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, false);
416 parent->Add(child); 484 parent->Add(child);
417 } 485 }
418 } 486 }
419 callback.Run(success); 487 callback.Run(success);
420 } 488 }
421 489
422 void ViewManagerConnection::RemoveNodeFromParent( 490 void ViewManagerConnection::RemoveNodeFromParent(
423 TransportNodeId node_id, 491 TransportNodeId node_id,
424 TransportChangeId server_change_id, 492 TransportChangeId server_change_id,
425 const Callback<void(bool)>& callback) { 493 const Callback<void(bool)>& callback) {
426 bool success = false; 494 bool success = false;
427 if (server_change_id == root_node_manager_->next_server_change_id()) { 495 if (server_change_id == root_node_manager_->next_server_change_id()) {
428 Node* node = GetNode(NodeIdFromTransportId(node_id)); 496 Node* node = GetNode(NodeIdFromTransportId(node_id));
429 if (node && node->GetParent()) { 497 if (CanRemoveNodeFromParent(node)) {
430 success = true; 498 success = true;
431 RootNodeManager::ScopedChange change( 499 RootNodeManager::ScopedChange change(
432 this, root_node_manager_, 500 this, root_node_manager_,
433 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, false); 501 RootNodeManager::CHANGE_TYPE_ADVANCE_SERVER_CHANGE_ID, false);
434 node->GetParent()->Remove(node); 502 node->GetParent()->Remove(node);
435 } 503 }
436 } 504 }
437 callback.Run(success); 505 callback.Run(success);
438 } 506 }
439 507
440 void ViewManagerConnection::GetNodeTree( 508 void ViewManagerConnection::GetNodeTree(
441 TransportNodeId node_id, 509 TransportNodeId node_id,
442 const Callback<void(Array<INode>)>& callback) { 510 const Callback<void(Array<INode>)>& callback) {
443 AllocationScope allocation_scope; 511 AllocationScope allocation_scope;
444 Node* node = GetNode(NodeIdFromTransportId(node_id)); 512 Node* node = GetNode(NodeIdFromTransportId(node_id));
445 std::vector<const Node*> nodes; 513 std::vector<const Node*> nodes;
446 GetDescendants(node, &nodes); 514 if (CanGetNodeTree(node)) {
447 for (size_t i = 0; i < nodes.size(); ++i) 515 GetDescendants(node, &nodes);
448 known_nodes_.insert(NodeIdToTransportId(nodes[i]->id())); 516 for (size_t i = 0; i < nodes.size(); ++i)
517 known_nodes_.insert(NodeIdToTransportId(nodes[i]->id()));
518 }
449 callback.Run(NodesToINodes(nodes)); 519 callback.Run(NodesToINodes(nodes));
450 } 520 }
451 521
452 void ViewManagerConnection::CreateView( 522 void ViewManagerConnection::CreateView(
453 TransportViewId transport_view_id, 523 TransportViewId transport_view_id,
454 const Callback<void(bool)>& callback) { 524 const Callback<void(bool)>& callback) {
455 const ViewId view_id(ViewIdFromTransportId(transport_view_id)); 525 const ViewId view_id(ViewIdFromTransportId(transport_view_id));
456 if (view_id.connection_id != id_ || view_map_.count(view_id.view_id)) { 526 if (view_id.connection_id != id_ || view_map_.count(view_id.view_id)) {
457 callback.Run(false); 527 callback.Run(false);
458 return; 528 return;
(...skipping 12 matching lines...) Expand all
471 view_id.connection_id); 541 view_id.connection_id);
472 did_delete = (connection && connection->DeleteViewImpl(this, view_id)); 542 did_delete = (connection && connection->DeleteViewImpl(this, view_id));
473 } 543 }
474 callback.Run(did_delete); 544 callback.Run(did_delete);
475 } 545 }
476 546
477 void ViewManagerConnection::SetView( 547 void ViewManagerConnection::SetView(
478 TransportNodeId transport_node_id, 548 TransportNodeId transport_node_id,
479 TransportViewId transport_view_id, 549 TransportViewId transport_view_id,
480 const Callback<void(bool)>& callback) { 550 const Callback<void(bool)>& callback) {
481 const NodeId node_id(NodeIdFromTransportId(transport_node_id)); 551 Node* node = GetNode(NodeIdFromTransportId(transport_node_id));
482 callback.Run(SetViewImpl(node_id, ViewIdFromTransportId(transport_view_id))); 552 const ViewId view_id(ViewIdFromTransportId(transport_view_id));
553 callback.Run(CanSetView(node, view_id) && SetViewImpl(node, view_id));
483 } 554 }
484 555
485 void ViewManagerConnection::SetViewContents( 556 void ViewManagerConnection::SetViewContents(
486 TransportViewId view_id, 557 TransportViewId view_id,
487 ScopedSharedBufferHandle buffer, 558 ScopedSharedBufferHandle buffer,
488 uint32_t buffer_size) { 559 uint32_t buffer_size) {
489 View* view = GetView(ViewIdFromTransportId(view_id)); 560 View* view = GetView(ViewIdFromTransportId(view_id));
490 if (!view) 561 if (!view)
491 return; 562 return;
492 void* handle_data; 563 void* handle_data;
(...skipping 26 matching lines...) Expand all
519 590
520 void ViewManagerConnection::OnNodeViewReplaced(const Node* node, 591 void ViewManagerConnection::OnNodeViewReplaced(const Node* node,
521 const View* new_view, 592 const View* new_view,
522 const View* old_view) { 593 const View* old_view) {
523 root_node_manager_->ProcessNodeViewReplaced(node, new_view, old_view); 594 root_node_manager_->ProcessNodeViewReplaced(node, new_view, old_view);
524 } 595 }
525 596
526 } // namespace service 597 } // namespace service
527 } // namespace view_manager 598 } // namespace view_manager
528 } // namespace mojo 599 } // namespace mojo
OLDNEW
« no previous file with comments | « mojo/services/view_manager/view_manager_connection.h ('k') | mojo/services/view_manager/view_manager_connection_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698